Расширение application.cfc в подкаталоге
У меня есть следующие два файла, и я хотел бы, чтобы второй расширил первый:
- Wwwroot \ сайт \ Application.cfc
- Wwwroot \ сайт \ реж \ Application.cfc
Однако, когда я иду, чтобы объявить компонент для второго файла, я не уверен, что поместить в атрибут extends. Моя проблема заключается в том, что несколько сайтов разработчиков (с общим SVN-репозиторием) работают на одном и том же экземпляре ColdFusion, поэтому я не могу просто создать отображение в администраторе CF следующим образом:
<cfcomponent extends="site.application">
Однако ColdFusion не нравится:
<cfcomponent extends="..application">
или любой динамический ввод, такой как:
<cfcomponent extends="#expandpath('..').#application">
Создание отображения во время выполнения ( как здесь) также не представляется возможным. Создание его в базовом application.cfc бесполезно, потому что этот код еще не был выполнен к моменту объявления наследующего cfc; и я не могу создать сопоставление до того, как будет определен наследующий компонент, потому что еще нет приложения для его подключения.
Есть ли способ, с помощью которого я могу ссылаться на родительский каталог для выполнения моих расширений?
Изменить, чтобы уточнить: Решение ApplicationProxy не работает из-за выделенного текста выше. Прямо сейчас, в качестве обходного пути, мы просто не проверяем \ dir \ application.cfc в SVN, чтобы каждый разработчик мог сохранить версию, расширяющую его / ее собственный корневой application.cfc. Очевидно, это не идеально.
4 ответа
Следующий код работает для меня. Однако я заметил, что application.cfc кэшируется, поэтому изменения в родительском приложении cfc могут не отражаться. Я справился с этим, сделав тривиальные изменения в дочернем приложении cfc.
<cfcomponent output="false">
<cfset variables.higherPath = ReReplace(GetMetaData(this).name,"\.[^\.]+\.[^\.]+$","") />
<cfset variables.extendApp = CreateObject("component", "#variables.higherPath#.Application") />
<cfloop item="variables.key" collection="#variables.extendApp#">
<cfif IsCustomFunction(variables.extendApp[variables.key])>
<cfset super[variables.key] = variables.extendApp[variables.key]>
<cfelse>
<cfset this[variables.key] = variables.extendApp[variables.key] >
</cfif>
</cfloop>
<cffunction name="onApplicationStart" output="false">
<cfset super.onApplicationStart() />
</cffunction>
У Шона Корфилда есть запись в блоге, объясняющая, как расширить корневой файл Application.cfc.
Ниже приведена соответствующая информация, скопированная из этой записи.
Вот ваш корневой CFC /Application.cfc:
<cfcomponent>
<cfset this.name = "cf7app" />
<cfset this.sessionmanagement = true />
</cfcomponent>
Вот ваш прокси CFC /ApplicationProxy.cfc:
<cfcomponent extends="Application">
</cfcomponent>
Он полностью пустой и служит просто для создания псевдонима для вашего корневого каталога /Application.cfc. Вот ваш подкаталог CFC /app/Application.cfc:
<cfcomponent extends="ApplicationProxy">
<cffunction name="onSessionStart">
<cfoutput><p>app.Application.onSessionStart()</p></cfoutput>
<cfset session.counter = 0 />
</cffunction>
<cffunction name="onRequestStart">
<cfoutput><p>app.Application.onRequestStart()</p></cfoutput>
<cfdump label="application" var="#application#"/>
</cffunction>
</cfcomponent>
Корень каждого отдельного сайта должен иметь свое собственное главное приложение:
/site1/Application.cfc
/site2/Application.cfc
/site3/Application.cfc
Все эти приложения являются отдельными отдельными приложениями, между которыми ничего нет.
Если на каком-либо из этих отдельных сайтов должны быть вложенные приложения, то рядом с мастером должен быть ApplicationProxy.cfc,
e.g.
/site1/ApplicationProxy.cfc
/site2/ApplicationProxy.cfc
Затем для каждого субприложения у вас есть тот, который расширяет прокси:
e.g.
/site1/subA/Application.cfc
/site1/subB/Application.cfc
/site2/subA/Application.cfc
Я знаю, что это старая тема, но я нашел способ сделать это (кажется, работает в моем тестировании) без использования сопоставлений CF Administrator.
Вы можете сделать это, добавив сопоставление для каждого приложения в свой дочерний файл Application.cfc, используя расширенный относительный путь:
<cfcomponent extends="cms.Application" output="false">
<cfset this.mappings["/cms"] = expandPath(getDirectoryFromPath(getCurrentTemplatePath()) & "../../../../")>
<cflog text="#getMetadata(this).extends.path#">
</cfcomponent>
Да, это кажется немного хакерским, но это похоже на работу.
Эдвард и др., я сослался на ваш комментарий в посте ниже. См. https://gregoryalexander.com/blog/2021/1/30/Extending-Applicationcfcs-using-mappings-and-proxy .
Вы абсолютно можете расширить cfc с помощью сопоставлений. Я должен был сделать это сам.
Одна из самых неприятных вещей, с которыми мне приходилось сталкиваться в ColdFusion, — это попытка создать внешнее приложение, открытое для широкой публики, и необходимость защитить часть этого сайта с помощью приложения в подпапке и расширения логики из базы. приложение.cfc. Я расскажу вам о текущем подходе, который разработчики используют для решения этой проблемы, а также покажу вам, как дополнительно использовать отображение, когда может быть хостинг-провайдер, использующий виртуальные каталоги.
Это довольно длинная статья, если вы хотите перейти к краткому изложению, прокрутите страницу вниз.
Много лет назад, когда я впервые попытался это сделать, я получил следующее сообщение, что бы я ни пытался сделать: «Не удалось найти компонент или интерфейс ColdFusion xxx». root и вложенные папки имеют одно и то же имя, т. е. Application.cfc, и ColdFusion не может правильно определить, какой компонент расширять.Наконец, после некоторых серьезных исследований, кому-то пришла в голову идея создать proxy.cfc, который находится в том же корневой каталог как корневой Application.cfc, а Application.cfc в подпапке расширяет пустой proxy.cfc, который расширяет корневой cfc следующим образом:
корневой каталог: Application.cfc Этот корневой Application.cfc ничего не расширяет.
Также в корневом каталоге: Proxy.cfcProxy.cfc имеет следующий код, по сути он пустой. Единственное, что делает Proxy.cfc, — это расширение Application.cfc, находящегося в том же каталоге:
Подкаталог, такой как папка с именем admin. В этом подкаталоге есть еще один Application.cfc. Допустим, этот компонент отвечает за безопасность приложения и имеет логику входа в систему, а также, например, настройки отладки. Этот Application.cfc расширит Proxy.cfc, чтобы получить методы и свойства Application.cfc в корневом каталоге следующим образом:
Этот подход был удачей, и о нем активно писали в блогах. Бен Надел сделал несколько очень полезных постов, которыми я поделюсь внизу этой статьи.
Это работает достаточно хорошо, если вы не находитесь в размещенном домене или на сервере, который использует виртуальные каталоги. В этом случае мы находимся в той же оригинальной лодке, в которой мы начали. Теперь мы вернулись к аду «Не удалось найти компонент или интерфейс ColdFusion xxx»!
Однако есть решение этой сложной проблемы, нам также нужно использовать отображение!
Распространенным заблуждением является то, что вы не можете использовать сопоставление для расширения компонентов. Я не совсем уверен, откуда изначально возникло это заблуждение, но было доказано, что это просто неправда. Бывают случаи, когда мы должны использовать сопоставление для решения некоторых раздражающих проблем, как здесь.
Этот конкретный сайт размещен на hostek.com. С ними приятно иметь дело, но сервер, на котором размещен мой сайт, имеет некоторые особенности из-за структуры каталогов. Здесь, когда я использую метод Proxy.cfc для расширения логики от базового Application.cfc до Application.cfc в папке администратора, я получаю ужасную ошибку «не удалось найти ... компонент». Когда я впервые увидел это, я был встревожен, думая, что это не повторится, поэтому я обратился к картированию CFC ColdFusion. Сопоставление сообщает ColdFusion, где найти файл и каковы отношения между файлами.
Давайте рассмотрим только что рассмотренную структуру CFC. Например, представьте себе следующую структуру каталогов:
корневой каталог: например , www.gregoryalexander.com/ подкаталог: www.gregoryalexander.com/admin/
Как уже говорилось, у нас есть Application.cfc и Proxy.cfc в корневом каталоге, и у нас есть Application.cfc в подкаталоге 'admin'. Proxy.cfc расширяет Application.cfc, также находящийся в корневом каталоге, а Application.cfc в подкаталоге (admin) расширяет Proxy.cfc в корневом каталоге.
корневой каталог: содержит как Application.cfc, так и Proxy.cfc (который расширяет корневой Application.cfc). подкаталог: Application.cfc (расширяет Proxy.cfc).
Теперь нам также нужно добавить следующее сопоставление в корневой Application.cfc. Эта логика сопоставления должна находиться в верхней части корневого файла Application.cfc и не должна находиться ни в одном из обработчиков событий Application.cfc (onApplicationStart, onApplicationRequest и т. д.). Этот код сопоставления не обязательно должен находиться где-либо еще, кроме корневого Application.cfc:
Я использовал rootCfc для идентификации Application.cfc в корневом каталоге, тогда как adminCfc применяется к приложению в каталоге admin. Эти переменные могут называться как угодно. Обратите внимание, что строка «/admin» в конце сопоставления adminCfc указывает на папку «admin», которая является подкаталогом.
Теперь, когда у нас есть сопоставления в корневом Application.cfc, нам нужно применить их к оператору extends в Application.cfc, расположенном в подкаталоге. В шаблоне /admin/Application.cfc используйте:
/admin/Приложение.cfc
Конечно, rootCfc указывает Application.cfc в подкаталоге искать шаблон Proxy.cfc в корневом каталоге. Как и другие операторы расширения, вам не нужно указывать «.cfc» в конце прокси.
Вам не нужно использовать это сопоставление «расширения» ни в корневых шаблонах Proxy.cfc, ни в Application.cfc. Они уже могут найти друг друга, так как оба находятся в одном корневом каталоге.
/Proxy.cfc
Резюме Для полной ясности: root Application.cfc Содержит логику сопоставления. Имеет сопоставления как для корня, так и для подкаталога. Не использует оператор «extend»
root Proxy.cfm Работает простой 'extends="Administrator". Нет логики отображения.
subdirectory Application.cfc В операторе extends должно быть имя переменной сопоставления папки (rootCfc), точка (.) и, наконец, имя шаблона Proxy.cfc без префикса .cfc (Proxy)
Приношу свои извинения за столь многословие. Я раздражал себя, когда писал это, но не так, как когда пытался решить эту проблему!
Заботиться!