To learn all about Skin Spider, click here.
To view the most updated application, click here.
To view the current code base, click here.
In my earlier updates, I created two ColdFusion component configuration objects, Config.cfc and PublicConfig.cfc. After some discussion on the blog, I have decided to go with the private Config.cfc. I am not crazy about having to make method calls to access things that I feel will not change very often. But, the method interface does allow for more flexibility and provides better protection from variance (PV). By hiding the internal workings of the Config.cfc I will be able to change what is going on in the Config.cfc without the dependent code being affected.
Building the configuration object was one step, the next step was applying it. First, I removed all inline config code from the Application.cfc ColdFusion component. Now, all config code should be in the Config.cfc ColdFusion component. As I was doing this, I realized that the Max Data Storage variable and the path to the data storage files should be moved to the Config.cfc as well as the rest of the config items. To accomodate this, I added the appropriate config variables as well as the "getter" methods for these values.
Then, I went through all the code and took out all references to the ColdFusion method, ExpandPath(). These paths, as well as all relative web paths (related to videos and images) were replaced with calls to the config object (ex. APPLICATION.Config.GetFullPaths().Videos). I did this in the following files:
As I was going through the code doing this, I realized that there was another item that I could move into the config object: the path to application executables. Remember, when we grab the links off of a thumbnail gallery page, we are taking a screen shot of the web page itself (spider_gallery.cfm). To do this, we are executing WebShotCMD via the ColdFusion CFExecute tag. In this application all executable are stored in "extensions/executables/" and this seemed like a good path to keep in the Config.cfc object. I added this path to both the relative and full paths within the Config.cfc configuration object.
That fact that as I was applying the programmable config object I found three more config items just goes to show that we are going to keep discovering ways to improve the system as we go. There is nothing wrong with having a good design up front. But, you never want to get sucked into "Analysis Paralysis" where you never move forward because you can't settle on a good design. Start off with a good base design, then just start coding. When you find a place to improve the code, improve it, but the important thing is just to get a move on.
As I was looking at the HTML that was being output after I applied the Config.cfc methodology, I realized that all the web paths were messed up. In the Config.cfc, the relative paths were "server" paths due to the CleanServerPath() method calls. The problem with that is that the slashes are different for web and server and I was using these "server" paths to build web links. To remedy this, I have made all the relative paths in the Config.cfc "web" paths by passing them through the CleanWebPath() function. I figure only the web paths will ever use these relative paths and, it won't affect the full paths as those are getting passed through the CleanServerPath() function anyway.
I hav been using request variables for my configuration information (set in a settings.cfm file), but I really like this approach. I may borrow it in future projects.
Your database schema XML looks almost exactly like the XML used to define a database schema for DataMgr. The only differences are that I use a "field" tag instead of a "column" tag (it would be very easy for me to make it accept either) and instead of a "type" attribute with the database datatype, I have a "CF_DataType" attribute with a value from the "cfsqltype" from the "cfqueryparam" tag. In retrospect, I wish that was what I had named my attribute.
I think the DataMgr approach could really fit what you are doing here (of course, I am biased ;)
I note that this is progressing nicely and REALLY LOOKS like a finished app, plenty of functionality, and I've downloaded it as something to pick apart and learn from the pieces...
Add to things to think of doing, when editing a movie/record, say on the second page, that on submitting it always takes you back to the first page. Since you were so kind as to allow adding tags without having to go back and choose add tags every time, consider adding a url or form variable to indicate what page the user was on when they chose to edit, and return them to that page.
And if it was just a senior moment on my part, ignore (if you can't reproduce the same behavior)
I am in agreement 100%. This is on the list of things to upgrade before I will consider Iteration 2 complete.
In order to do this, I am going to come up with a sort of interal bread crumbing system where each page is represented by a given URL. Then I will figure out how to send the user back to the more recent "referrer".
The tricky part is that with pages like a form where (due to data validation) I might have multiple submites to the same page, I have to come up with a way to not use the first form load as the referrer for the second form load.
Should be exciting as it probably the biggest thing left to do for iteration 2.
I am glad you liking the app-in-progress. Please feel free to make any and all suggestions. It's always appreciated.