1+ <cfsetting enablecfoutputonly =" true" />
2+ <!--- @@displayname: CDN Migration Tool --->
3+
4+ <cfimport taglib =" /farcry/core/tags/admin" prefix =" admin" />
5+ <cfimport taglib =" /farcry/core/tags/formtools" prefix =" ft" />
6+ <cfimport taglib =" /farcry/core/tags/webskin" prefix =" skin" />
7+
8+
9+ <cfif isdefined (" url.reset_typename" ) and isdefined (" url.reset_typename" ) and isdefined (" url.reset_property" ) >
10+
11+ <cfset stResult = structnew () />
12+ <cfset stResult [" typename" ] = url .reset_typename />
13+ <cfset stResult [" objectid" ] = url .reset_objectid />
14+ <cfset stResult [" property" ] = url .reset_property />
15+
16+ <cfset stObj = application .fapi .getContentObject (typename = url .reset_typename ,objectid = url .reset_objectid ) />
17+
18+ <cfif application .fapi .getPropertyMetadata (url .reset_typename , url .reset_property , " ftType" , " " ) eq " image" and len (application .fapi .getPropertyMetadata (url .reset_typename , url .reset_property , " ftSourceField" , " " )) >
19+ <cfset sourceField = listfirst (application .fapi .getPropertyMetadata (url .reset_typename , url .reset_property , " ftSourceField" )," :" ) />
20+ <cfset stFP = {} />
21+ <cfset stFP [sourceField ] = {
22+ value = stObj [sourceField ]
23+ } />
24+ <cfset stFP [url .reset_property ] = structnew () />
25+ <cfset oldVal = stObj [url .reset_property ] />
26+ <cfset stObj [url .reset_property ] = " " />
27+
28+ <cftry >
29+ <cfset stObj = application .formtools .image .oFactory .ImageAutoGenerateBeforeSave (typename = stObj .typename ,stProperties = stObj ,stFields = application .stCOAPI [url .reset_typename ].stProps ,stFormPost = stFP ) />
30+
31+ <cfif stObj [url .reset_property ] neq oldVal >
32+ <cfset application .fapi .setData (stProperties = stObj ) />
33+ </cfif >
34+
35+ <cfset stResult [" success" ] = true />
36+ <cfset stResult [" file" ] = stObj [url .reset_property ] />
37+
38+ <cfcatch >
39+ <cfset stResult [" success" ] = false />
40+ <cfset stResult [" error" ] = cfcatch .message />
41+ </cfcatch >
42+ </cftry >
43+ </cfif >
44+
45+ <cfcontent type =" text/json" variable =" #ToBinary ( ToBase64 ( serializeJSON (stResult ) ) ) #" reset =" Yes" >
46+ </cfif >
47+
48+
49+ <cfparam name =" form.copy" default =" missing" />
50+ <cfparam name =" form.step" default =" select-type" />
51+
52+
53+ <admin:header >
54+
55+ <cfif form .step eq " select-type" >
56+ <cfset qTypes = querynew (" typename,typelabel,properties" ) />
57+
58+ <cfloop collection =" #application .stCOAPI #" item =" thistype" >
59+ <cfif listcontains (" type,rule" ,application .stCOAPI [this type ].class ) >
60+ <cfloop collection =" #application .stCOAPI [this type ].stProps #" item =" thisprop" >
61+ <cfif application .fapi .getPropertyMetadata (this type , this prop , " ftType" , " string" ) eq " image" and len (application .fapi .getPropertyMetadata (this type , this prop , " ftSourceField" , " " )) >
62+ <cfif qTypes .typename [qTypes .recordcount ] neq this type >
63+ <cfset queryaddrow (qTypes ) />
64+ </cfif >
65+
66+ <cfset querysetcell (qTypes ," typename" ,this type ) />
67+ <cfset querysetcell (qTypes ," typelabel" ,application .stCOAPI [this type ].displayname ) />
68+ <cfset querysetcell (qTypes ," properties" ,listappend (qTypes .properties [qTypes .recordcount ],application .fapi .getPropertyMetadata (this type , this prop , " ftLabel" , this prop ))) />
69+ </cfif >
70+ </cfloop >
71+ </cfif >
72+ </cfloop >
73+
74+ <cfquery dbtype =" query" name =" qTypes" >
75+ select * from qTypes order by typelabel
76+ </cfquery >
77+
78+ <skin:htmlHead ><cfoutput >
79+ <style >
80+ .selected , .selected td { background-color :##F9E6D4 ; }
81+ th .select , td .select { width :40px ; }
82+ th .insource , td .insource , th .intarget , td .intarget { width :80px ; }
83+ ##files th .insource , td .insource { text-align :right ; }
84+ td .insource , td .intarget , td .status { font-weight :bold ; }
85+ .in-location-Yes { color :##01a100 ; }
86+ .in-location-No { color :##FF0000 ; }
87+ th .status , td .status { width :80px ; }
88+ .status-not-applicable { color :##666666 ; }
89+ .status-success { color :##01a100 ; }
90+ .status-failure { color :##FF0000 ; }
91+ </style >
92+ </cfoutput ></skin:htmlHead >
93+
94+ <cfoutput >
95+ <h1 ><admin:resource key =" webtop.utilities.cdnmigrator@title" >Cloudinary Reset Tool</admin:resource ></h1 >
96+ <admin:resource key =" webtop.utilities.coapisqllog.blurb@html" >
97+ <p >This tool makes it easy to reset stored Cloudinary URLs.</p >
98+ </admin:resource >
99+ </cfoutput >
100+
101+ <ft:form >
102+ <ft:buttonPanel >
103+ <ft:button value =" Select Types" />
104+ </ft:buttonPanel >
105+
106+ <cfoutput ><input type =" hidden" name =" step" value =" review-files" ></cfoutput >
107+
108+ <ft:field label =" Types" bMultiField =" true" class =" blockLabels" >
109+ <cfoutput >
110+ <table id =" files" class =" objectAdmin" style =" width:100%;table-layout:fixed;" >
111+ <thead >
112+ <tr >
113+ <th class =" select" ></th >
114+ <th class =" type" >Type</th >
115+ <th class =" property" >Properties</th >
116+ </tr >
117+ </thead >
118+ <tbody >
119+ </cfoutput >
120+
121+ <cfoutput query =" qTypes" >
122+ <tr id =" type-#qTypes .currentrow #" class =" type <cfif qTypes.currentrow mod 2>alt</cfif>" >
123+ <td class =" select" ><input type =" checkbox" name =" types" value =" #qTypes .typename #" ></td >
124+ <td class =" type" >#qTypes .typelabel #</td >
125+ <td class =" property" >#replace (qTypes .properties ," ," ," , " ," ALL" ) #</td >
126+ </tr >
127+ </cfoutput >
128+
129+ <cfoutput >
130+ </tbody >
131+ </table >
132+ </cfoutput >
133+
134+ <ft:buttonPanel >
135+ <ft:button value =" Select Types" />
136+ </ft:buttonPanel >
137+ </ft:field >
138+ </ft:form >
139+
140+ <cfelseif form .step eq " review-files" >
141+ <cfset qWrong = querynew (" typename,typelabel,property,seq,objectid,label,filename" ," varchar,varchar,varchar,integer,varchar,varchar,varchar" ) />
142+
143+ <cfloop collection =" #application .stCOAPI #" item =" thistype" >
144+ <cfif listfindnocase (form .types ,this type ) and listcontains (" type,rule" ,application .stCOAPI [this type ].class ) >
145+ <cfloop collection =" #application .stCOAPI [this type ].stProps #" item =" thisprop" >
146+ <cfif application .fapi .getPropertyMetadata (this type , this prop , " ftType" , " string" ) eq " image" and len (application .fapi .getPropertyMetadata (this type , this prop , " ftSourceField" , " " )) >
147+ <cfset o = application .fapi .getContentType (typename = this type ) />
148+ <cfquery datasource =" #application .dsn #" name =" q" >
149+ select objectid,label,#this prop #
150+ from #application .dbowner ##this type #
151+ </cfquery >
152+
153+ <cfloop query =" q" >
154+ <cfset queryaddrow (qWrong ) />
155+ <cfset querysetcell (qWrong ," typename" ,this type ) />
156+ <cfset querysetcell (qWrong ," typelabel" ,application .stCOAPI [this type ].displayname ) />
157+ <cfset querysetcell (qWrong ," property" ,this prop ) />
158+ <cfset querysetcell (qWrong ," seq" ,application .stCOAPI [this type ].stProps [this prop ].metadata .ftSeq ) />
159+ <cfset querysetcell (qWrong ," objectid" ,q .objectid ) />
160+ <cfset querysetcell (qWrong ," label" ,q .label ) />
161+ <cfset querysetcell (qWrong ," filename" ,q [this prop ][q .currentrow ]) />
162+ </cfloop >
163+ </cfif >
164+ </cfloop >
165+ </cfif >
166+ </cfloop >
167+
168+ <cfquery dbtype =" query" name =" qWrong" >
169+ select *
170+ from qWrong
171+ order by typelabel, property, label, objectid, seq
172+ </cfquery >
173+
174+ <skin:htmlHead ><cfoutput >
175+ <style >
176+ .selected , .selected td { background-color :##F9E6D4 ; }
177+ th .select , td .select { width :40px ; }
178+ th .insource , td .insource , th .intarget , td .intarget { width :80px ; }
179+ ##files th .insource , td .insource { text-align :right ; }
180+ td .insource , td .intarget , td .status { font-weight :bold ; }
181+ .in-location-Yes { color :##01a100 ; }
182+ .in-location-No { color :##FF0000 ; }
183+ th .status , td .status { width :80px ; }
184+ .status-not-applicable { color :##666666 ; }
185+ .status-success { color :##01a100 ; }
186+ .status-failure { color :##FF0000 ; }
187+ </style >
188+ <script type =" text/javascript" >
189+ var processing = false ;
190+ var processingfile = - 1 ;
191+
192+ function getNextFile (){
193+ var file = $j (" ##files tbody input[name=files]:checked" ).first ().parents (" tr" );
194+
195+ if (file .size ()){
196+ return file .data (" file" ) - 1 ;
197+ }
198+ else {
199+ return - 1 ;
200+ }
201+ }
202+
203+ function copyFiles (action ){
204+ if (action=== " toggle" && processing && processingfile> - 1 ){
205+ processing = false ;
206+ }
207+ else if ((action=== " next" && processing) || (action=== " toggle" && ! processing)){
208+ processing = true ;
209+ processingfile = getNextFile ();
210+
211+ if (processingfile> - 1 ){
212+ var info = $j (" ##file-" + (processingfile+ 1 )+ " input" ).val ().split (" |" );
213+ $j .getJSON (" #application.fapi.fixURL()#&reset_typename=" + info[0 ]+ " &reset_objectid=" + info[1 ]+ " &reset_property=" + info[2 ],function (data ){
214+ if (data .success ){
215+ $j (" ##file-" + (processingfile+ 1 ))
216+ .removeClass (" selected" )
217+ .find (" input[name=files]" ).attr (" checked" ,null ).end ()
218+ .find (" .status" ).removeClass (" status-not-applicable" ).removeClass (" status-success" ).removeClass (" status-failure" ).addClass (" status-success" ).html (" Done" ).attr (" title" ," " ).end ()
219+ .find (" .file" ).html (data .file );
220+ }
221+ else {
222+ $j (" ##file-" + (processingfile+ 1 ))
223+ .removeClass (" selected" )
224+ .find (" input[name=files]" ).attr (" checked" ,null ).end ()
225+ .find (" .status" ).removeClass (" status-not-applicable" ).removeClass (" status-success" ).removeClass (" status-failure" ).addClass (" status-failure" ).html (" Error" ).attr (" title" ,data .error ).end ();
226+ }
227+
228+ copyFiles (" next" );
229+ });
230+ }
231+ else {
232+ processing = false ;
233+ }
234+ }
235+ };
236+ </script >
237+ </cfoutput >
238+ <skin:onReady ><cfoutput >
239+ $j("## allfiles").click(function(){
240+ var tr = $j("## files tbody input[name=files]").attr("checked",$j(this).attr("checked")==="checked"?"checked":null).parents("tr.file");
241+
242+ if ($j(this).attr("checked")==="checked")
243+ tr.addClass("selected");
244+ else
245+ tr.removeClass("selected")
246+ });
247+ $j("## files tbody tr").click(function(event){
248+ var target = $j(event.target), input = $j("input[name=files]",this), self = $j(this);
249+
250+ if (!target.is("input"))
251+ input.attr("checked",input.attr("checked")==="checked"?null:"checked");
252+
253+ if (input.attr("checked") === "checked")
254+ self.addClass("selected");
255+ else
256+ self.removeClass("selected");
257+ });
258+ </cfoutput ></skin:onReady >
259+
260+ <cfoutput >
261+ <h1 ><admin:resource key =" webtop.utilities.cdnmigrator@title" >Cloudinary Reset Tool</admin:resource ></h1 >
262+ <admin:resource key =" webtop.utilities.coapisqllog.blurb@html" >
263+ <p >This tool makes it easy to reset stored Cloudinary URLs.</p >
264+ </admin:resource >
265+ </cfoutput >
266+
267+ <ft:form >
268+ <ft:buttonPanel >
269+ <cfif qWrong .recordcount >
270+ <ft:button value =" Reset URLs" onclick =" copyFiles('toggle');return false;" />
271+ </cfif >
272+ </ft:buttonPanel >
273+
274+ <cfif qWrong .recordcount >
275+ <ft:field label =" Files" bMultiField =" true" class =" blockLabels" >
276+ <cfoutput >
277+ <table id =" files" class =" objectAdmin" style =" width:100%;table-layout:fixed;" >
278+ <thead >
279+ <tr >
280+ <th class =" select" ><input type =" checkbox" id =" allfiles" ></th >
281+ <th class =" type" >Type</th >
282+ <th class =" property" >Property</th >
283+ <th class =" title" >Object</th >
284+ <th class =" file" >File</th >
285+ <th class =" status" >Status</th >
286+ </tr >
287+ </thead >
288+ <tbody >
289+ </cfoutput >
290+
291+ <cfoutput query =" qWrong" >
292+ <tr id =" file-#qWrong .currentrow #" class =" file <cfif qWrong.currentrow mod 2>alt</cfif>" data-typename =" #qWrong .typename #" data-property =" #qWrong .property #" data-file =" #qWrong .currentrow #" >
293+ <td class =" select" ><input type =" checkbox" name =" files" value =" #qWrong .typename #|#qWrong .objectid #|#qWrong .property #" ></td >
294+ <td class =" type" >#qWrong .typelabel # (<a class =" select-by-typename" data-typename =" #qWrong .typename #" >select all</a >)</td >
295+ <td class =" property" >#qWrong .property # (<a class =" select-by-property" data-typename =" #qWrong .typename #" data-property =" #qWrong .property #" >select all</a >)</td >
296+ <td class =" title" >#qWrong .label #</td >
297+ <td class =" file" >#qWrong .filename #</td >
298+ <td class =" status status-not-applicable" >N/A</td >
299+ </tr >
300+ </cfoutput >
301+
302+ <cfoutput >
303+ </tbody >
304+ </table >
305+ <script >
306+ $j (" .select-by-typename" ).bind (" click" ,function (e ){
307+ var self = $j (this );
308+ var typename = self .data (" typename" );
309+
310+ $j (' tr[data-typename=' + typename+ ' ] input[type=checkbox]' )
311+ .prop (' checked' ,true );
312+
313+ e .stopPropagation ();
314+ e .preventDefault ();
315+ });
316+ $j (" .select-by-property" ).bind (" click" ,function (e ){
317+ var self = $j (this );
318+ var typename = self .data (" typename" );
319+ var property = self .data (" property" );
320+
321+ $j (' tr[data-typename=' + typename+ ' ][data-property=' + property+ ' ] input[type=checkbox]' )
322+ .prop (' checked' ,true );
323+
324+ e .stopPropagation ();
325+ e .preventDefault ();
326+ });
327+ </script >
328+ </cfoutput >
329+ </ft:field >
330+
331+ <ft:buttonPanel >
332+ <ft:button value =" Copy Files" onclick =" copyFiles('toggle');return false;" />
333+ </ft:buttonPanel >
334+ </cfif >
335+ </ft:form >
336+ </cfif >
337+
338+ <admin:footer >
339+
340+ <cfsetting enablecfoutputonly =" false" />
0 commit comments