I need to auto-generate different aliases from two articles with the same title in Joomla 3.3. The user will add articles in the front end. I found this code:
<?php
defined( '_JEXEC' ) or die;
class plgContentRandom_Alias extends JPlugin
{
function onContentBeforeSave($context, &$article, $isNew) {
if(!$isNew){
return;
}
$alias = $article->alias;
$n = substr( "abcdefghijklmnopqrstuvwxyz" ,mt_rand( 0 ,25 ) ,1 ) .substr( md5( time( ) ) ,1 );
$table = JTable::getInstance('content');
while ($table->load(array('alias' => $alias))) {
$new_alias = $alias . $n;
}
$article->alias = $new_alias;
return true;
}
}
?>
, and made a plugin for Joomla, but the plugin not working in Joomla 3.3.
Any suggestions?
You can write your own plugin using the following code, although this functionality should be already part of joomla core.
I've used this because of Seblod error when using its insert content form.
Files:
Joomla installer descriptor:
uniqueAliasGenerator.xml
<?xml version="1.0" encoding="utf-8"?>
<extension version="3.1" type="plugin" group="content" method="upgrade">
<name>Content - Unique alias generator</name>
<author>McGiogen</author>
<creationDate>May 2015</creationDate>
<copyright></copyright>
<license></license>
<authorEmail>mcgiogen#hotmail.it</authorEmail>
<authorUrl>www.joomla.org</authorUrl>
<version>1.0</version>
<description>
Automatic generator of unique alias.
At save time it append "-X" (where X is a numeric identifier)
if article alias is already in database.
</description>
<files>
<filename plugin="uniqueAliasGenerator">uniqueAliasGenerator.php</filename>
<filename>index.html</filename>
</files>
<config>
</config>
</extension>
Plugin code:
uniqueAliasGenerator.php
<?php
// no direct access
defined( '_JEXEC' ) or die( 'Restricted access' );
class plgContentUniqueAliasGenerator extends JPlugin
{
/**
* Alias check and generation before save content method.
* Content is passed by reference. Method is called before the content is saved.
*
* #param string $context The context of the content passed to the plugin (added in 1.6).
* #param object $article A JTableContent object.
* #param bool $isNew If the content is just about to be created.
*
* #return void
*/
public function onContentBeforeSave($context, $article, $isNew)
{
if ($context == 'com_content.article' && $article->alias && $isNew) {
$oldAlias = $article->alias;
$categoryId = $article->catid; //An alias must be unique only in its category
$article->alias = $this->getUniqueAlias($oldAlias, $categoryId);
}
return true;
}
/**
* Find unique Alias name if current doesn't exist.
* #param string $alias Alias of the article
* #param string $catId Id of article's category
*
* #return string Return the unique alias value.
*/
protected function getUniqueAlias($alias, $catId)
{
$alias_ini = $alias;
for ($i = 2; $this->isAliasExist($alias, $catId); $i++) {
$alias = $alias_ini . '-' . $i;
}
return $alias;
}
/**
* Check the 'alias' in the database.
*
* #return boolean If found return true else false.
*/
protected function isAliasExist($alias, $catId)
{
$db = JFactory::getDBO();
$query = $db->getQuery(true);
$query
->select('COUNT(*)')
->from($db->quoteName('#__content')) //Articles table
->where($db->quoteName('alias') . ' = ' . $db->quote($alias))
->where($db->quoteName('catid') . ' = ' . $db->quote($catId)); //Category ID
$db->setQuery($query);
return ($db->loadResult() ? true : false);
}
}
?>
index.html
<!DOCTYPE html><title></title>
How to use:
Create files with the same names, put them in a folder called "uniqueAliasGenerator", zip in "uniqueAliasGenerator.zip", upload and install on your joomla.
Compatible with Joomla 3.x, tested on Joomla 3.4.1
Update 11 Nov 2017
Added check of $isNew. Thanks #robert-drygas.
In McGiogen code the line
if ($context == 'com_content.article' && $article->alias) {
can be write as
if ($context == 'com_content.article' && $article->alias && $isNew) {
so unique alias will be ganerated only for the new articles (without altered existing aliases when editing old articles).
Related
I want to change a constant in my Extension in the Controller via initializeAction.
It works the half way. Let me explain this:
TYPO3 Version 8.7.7 Extension build with Extension Builder.
If i use the following code in my UserController.php
/**
* initialize the controller
*
* #return void
*/
protected function initializeAction()
{
...
$this->settings['groupDefaultId'] = (string)$newUserGroup[$key]->getUid();
...
}
and i'll debug it after that in php i got the following Debuginformation:
settings
array(12 items)
groupDefaultId => '53' (2 chars)
This is the correct value in PHP for now. But if i check that value in the Backend under Template > Constant Editor the value isn't stored any more.
I tried the code above and the setConfiguration API function.
When i got the new ID, which one i want to set in constants i start the function with the following command:
File: BaseController.php
(my UserController extends BaseController, for splitting CRUD-function from Other-functions).
I give a string to it, because at the end of this "way" all Settings are stored as string in $this->settings.
// Set current Group Uid as defaultGroupId in Constants
$currentGroupIdHasSetInConstants = $this->setNewGroupIdInConstants((string)$newUserGroup[$key]->getUid());
We jumpt to the setNewGroupIdInConstants function:
File: BaseController.php
/**
* Sets the Constant 'defaultGroupId' with new Value
*
* Incoming Requirement for this function: defaultGroupId = 0 this means
* defaultGroupId is not set in Constants
*
* #param string $newdefaultGroupId New Default Group ID for New Users
* #return bool TRUE defaultGroupId has changed | FALSE no changes done
*/
public function setNewGroupIdInConstants(string $newdefaultGroupId)
{
// Rebuild constants with new property and value
$newConstantsValue = $this->addConstantsConfigurationForDefaultGroupId($newdefaultGroupId);
// Add the new property with value to constants
return $this->userRepository->updateConstants($newConstantsValue);
}
First this function jumps to addConstantsConfigurationForDefaultGroupId function:
In File: BaseController.php
/**
* Build new constants value for defaultGroupId
*
* #param string $value The new value for defaultGroupId
* #return string The complete Constants value
* including the defaultGroupId Configuration
*/
public function addConstantsConfigurationForDefaultGroupId($value)
{
$getConstants = $this->userRepository->fetchConstants()['constants'];
// This Value has to look like this with the new line (for getting original code incl. \n for constants)
$buildAdditionalConstant = '
plugin.tx_rmregistration.settings.defaultGroupId = '.$value;
return $getConstants.$buildAdditionalConstant;
}
fetchConstants function:
In File: UserRepository.php
(Usually it belongs to a SysTemplatesRepository.php, but those one doesn't exist. "Hello Core Team, we need a SysTemplatesRepository ;)".
/**
* Find Constants via sys_template Database Table
*
* #return array|NULL Result is array('constants' => queryResult) or NULL
*/
public function fetchConstants()
{ //
// Query Builder for Table: sys_template
$queryBuilder = GeneralUtility::makeInstance(ConnectionPool::class)->getQueryBuilderForTable('sys_template');
// Get Constants of Row, where RM Registration is included
$query = $queryBuilder
->select('constants')
->from('sys_template')
->where(
$queryBuilder->expr()->like(
'include_static_file',
$queryBuilder->createNamedParameter('%' . $queryBuilder->escapeLikeWildcards('EXT:rmregistration/Configuration/TypoScript') . '%')
)
);
// Execute Query and Return the Query-Fetch
$query = $queryBuilder->execute();
return $query->fetch();
}
Here is my code of the updateConstants function
In File: UserRepository.php
/**
* Update Constants via sys_template Database Table ( Updates $this->settings )
*
* #param string $constants The new settings, that has to be stored in $this->settings
*/
public function updateConstants(string $constants)
{
// Query Builder for Table: sys_template
$queryBuilder = GeneralUtility::makeInstance(ConnectionPool::class)->getQueryBuilderForTable('sys_template');
$query = $queryBuilder
->update('sys_template')
->where(
$queryBuilder->expr()->like(
'include_static_file',
$queryBuilder->createNamedParameter('%' . $queryBuilder->escapeLikeWildcards('EXT:rmregistration/Configuration/TypoScript') . '%')
)
)
->set('constants', $constants);
$query = $queryBuilder->execute();
return ($query > 0) ? TRUE : FALSE;
}
I'm building the admin for a Magento2 store (currently on 2.1.7, they want to use the newest version until we go live and then want to stabilize a particular version). The module in question is supposed to display all existing orders, with an actionsColumn that contains links to cancel, edit, and open a detailed overview of the purchased items associated with that order. The order detail page contains a grid view that should display all order items associated with an order number passed in the URL.
In order to filter out Order Items that don't relate to the specific Order Number, I've extended the \Magento\Framework\View\Element\UiComponent\DataProvider\SearchResult class. This works except for one weird caveat. If, in the addFieldToFilter call, I replace $ordNum with, say, '10000', it grabs the correct data. When using $ordNum to call this dynamically, however, it returns no rows at all. This despite trying all sorts of casting and === checks to ensure that there's no difference between the hardcoded and dynamic values. Is this a Magento bug? I can't at all figure out why this would be the case.
<?php
class OrderItems extends \Magento\Framework\View\Element\UiComponent\DataProvider\SearchResult
{
protected function _initSelect()
{
$this->filterByOrderNum();
parent::_initSelect();
return $this;
}
private function filterByOrderNum()
{
$request = \Magento\Framework\App\ObjectManager::getInstance()
->get('Magento\Framework\App\Request\Http');
$ordNum = $request->getParam('order_num');
$this->addFieldToFilter('order_num', ['eq' => $ordNum]); //if I switch this to hardcoded 10000, this works. With the variable, no dice.
return $this;
}
}
I just fixed it by using mentioned below steps
Store param value in session in controller
public function execute() {
$this->_catalogSession->setTokenId($this->request->getParam('entity_id'));
$this->_view->loadLayout();
$this->_view->loadLayoutUpdates();
$this->_view->getPage()->getConfig()->getTitle()->set(__('Redeem Token History'));
$this->_view->renderLayout();
}
Use session value in dataprovider
$tokensCollection->addFieldToFilter('token_id', ['eq' => $this->_catalogSession->getTokenId()]);
Enjoy :)
Try this in place of the getParam statement:
$url = parse_url($request);
$path = explode('/',$url['path']);
$ordNum = $path[3];
Just to make sure we are on the same page, this is the full code:
<?php
class OrderItems extends \Magento\Framework\View\Element\UiComponent\DataProvider\SearchResult
{
protected function _initSelect()
{
$this->filterByOrderNum();
parent::_initSelect();
return $this;
}
private function filterByOrderNum()
{
$request = \Magento\Framework\App\ObjectManager::getInstance()
->get('Magento\Framework\App\Request\Http');
$url = parse_url($request);
$path = explode('/',$url['path']);
$ordNum = $path[3];
$this->addFieldToFilter('order_num', $ordNum); //if I switch this to hardcoded 10000, this works. With the variable, no dice.
return $this;
}
}
We have solved this issue by doing the following :
/**
* CcCustompriceProductListingDataProvider constructor.
* #param string $name
* #param string $primaryFieldName
* #param string $requestFieldName
* #param \Magento\Framework\Api\Search\ReportingInterface $reporting
* #param \Magento\Framework\Api\Search\SearchCriteriaBuilder $searchCriteriaBuilder
* #param \Magento\Framework\App\RequestInterface $request
* #param \Magento\Framework\Api\FilterBuilder $filterBuilder
* #param array $meta
* #param array $data
* #throws \Exception
*/
public function __construct(
$name,
$primaryFieldName,
$requestFieldName,
ReportingInterface $reporting,
SearchCriteriaBuilder $searchCriteriaBuilder,
RequestInterface $request,
FilterBuilder $filterBuilder,
array $meta = [],
array $data = []
) {
$data['config']['filter_url_params']['product_id'] = $request->getParam('cppc_product_id', 0);
parent::__construct($name, $primaryFieldName, $requestFieldName, $reporting, $searchCriteriaBuilder, $request, $filterBuilder, $meta, $data);
}
You do not need to use any other function. The reason why this is is because it is also updated with an update URL and that does not have that parameter. By using adding that to the data it also parses that into the update url.
You can see that here (Parent function)
/**
* #return void
*/
protected function prepareUpdateUrl()
{
if (!isset($this->data['config']['filter_url_params'])) {
return;
}
foreach ($this->data['config']['filter_url_params'] as $paramName => $paramValue) {
if ('*' == $paramValue) {
$paramValue = $this->request->getParam($paramName);
}
if ($paramValue) {
$this->data['config']['update_url'] = sprintf(
'%s%s/%s/',
$this->data['config']['update_url'],
$paramName,
$paramValue
);
$this->addFilter(
$this->filterBuilder->setField($paramName)->setValue($paramValue)->setConditionType('eq')->create()
);
}
}
}
I'm new to Kohana, using version 3.3.3.1, I'm trying to build a simple dynamic site with the content/pages stored in mySQL DB. The site should have multiple languages. I tried searching everywhere for a good solution/module but I couldn't find anything that works with latest version of Kohana. I tried also this: https://github.com/shockiii/kohana-multilang but it's not working on the latest kohana.
I want to put the language in URL like this (and possibly hide the parameter for the default language):
http://www.domain.com/topics/page-name-here.html -- this would be default EN
http://www.domain.com/de/test/some-page-name-here.html
http://www.domain.com/fr/category/other-page-name-here.html
In my bootstrap.php I have the following route (before adding the language logic):
Route::set('page', '(<category>)(/<pagename>.html)', array(
'category' => '.*',
'pagename' => '.*'))
->defaults(array(
'controller' => 'Page',
'action' => 'index',
));
I want to have all this multi-language logic inside a module if possible. But I read about overriding the Request, URL, Route, and other classes to be able to do that.
What is the best way I can do this? What should I do/change and where to start?
I know this is more a general question, but any help or guidance is greatly appreciated.
Thanks very much!
1) add <lang> into routes in bootstrap.php:
Route::set('default', '((<lang>)(/)(<controller>)(/<action>(/<id>)))', array('lang' => "({$langs_abr})",'id'=>'.+'))
->defaults(array(
'lang' => $default_lang,
'controller' => 'Welcome',
'action' => 'index',
));
- define $default_lang somehow - I use siteconfig.php file placed inside application/config -see below.
2) Extend/redefine factory method in Request Controller:
<?php defined('SYSPATH') or die('No direct script access.');
class Request extends Kohana_Request {
/**
* Main request singleton instance. If no URI is provided, the URI will
* be automatically detected using PATH_INFO, REQUEST_URI, or PHP_SELF.
*
* #param string URI of the request
* #return Request
*/
public static function factory( $uri = TRUE,$client_params = array(), $allow_external = TRUE, $injected_routes = array())
{
$instance = parent::factory($uri);
$index_page = Kohana::$index_file;
$siteconfig = Model_Siteconfig::load();
$lang_uri_abbr = $siteconfig['lang_uri_abbr'];
$default_lang = $siteconfig['language_abbr'];
$lang_ignore = $siteconfig['lang_ignore'];
$ignore_urls = $siteconfig['ignore_urls'];
/* get the lang_abbr from uri segments */
$segments = explode('/',$instance->detect_uri());
$uri_detection = array_intersect($segments, $ignore_urls);
if(empty($uri_detection))
{
$lang_abbr = isset($segments[1]) ? $segments[1]:'';
/* get current language */
$cur_lang = $instance->param('lang',$default_lang);
/* check for invalid abbreviation */
if( ! isset($lang_uri_abbr[$lang_abbr]))
{
/* check for abbreviation to be ignored */
if ($cur_lang != $lang_ignore) {
/* check and set the default uri identifier */
$index_page .= empty($index_page) ? $default_lang : "/$default_lang";
/* redirect after inserting language id */
header('Location: '.URL::base().$index_page . $instance->detect_uri());
die();
}
}
}
return $instance;
}
}
I use "siteconfig" array with language definitions:
array(
'language_abbr' => 'cs',
'lang_uri_abbr' => array("cs" => "Ĩesky", "en" => "english"),
'lang_ignore' => 'it',
)
3) Extend/redefine "redirect" method in Controller class for automatic language adding:
<?php defined('SYSPATH') or die('No direct script access.');
class Controller extends Kohana_Controller {
/**
* Issues a HTTP redirect.
*
* Proxies to the [HTTP::redirect] method.
*
* #param string $uri URI to redirect to
* #param int $code HTTP Status code to use for the redirect
* #throws HTTP_Exception
*/
public static function redirect($uri = '', $code = 302)
{
$lng = Request::current()->param('lang');
return HTTP::redirect( (string) '/'.$lng.$uri, $code);
}
}
If You would use HTML class (for templates for example), you should probably redefine some other methods like "anchor" for creating anchors with automatic language adding:
<?php defined('SYSPATH') OR die('No direct script access.');
class HTML extends Kohana_HTML {
/**
* Create HTML link anchors. Note that the title is not escaped, to allow
* HTML elements within links (images, etc).
*
* echo HTML::anchor('/user/profile', 'My Profile');
*
* #param string $uri URL or URI string
* #param string $title link text
* #param array $attributes HTML anchor attributes
* #param mixed $protocol protocol to pass to URL::base()
* #param boolean $index include the index page
* #return string
* #uses URL::base
* #uses URL::site
* #uses HTML::attributes
*/
public static function anchor($uri, $title = NULL, array $attributes = NULL, $protocol = NULL, $index = FALSE)
{
//default language
$lng = Request::current()->param('lang');
if ($title === NULL)
{
// Use the URI as the title
$title = $uri;
}
if ($uri === '')
{
// Only use the base URL
$uri = URL::base($protocol, $index).$lng;
}
else
{
if (strpos($uri, '://') !== FALSE)
{
if (HTML::$windowed_urls === TRUE AND empty($attributes['target']))
{
// Make the link open in a new window
$attributes['target'] = '_blank';
}
}
elseif ($uri[0] !== '#')
{
// Make the URI absolute for non-id anchors
$uri = URL::site($lng.$uri, $protocol, $index);
}
}
// Add the sanitized link to the attributes
$attributes['href'] = $uri;
return '<a'.HTML::attributes($attributes).'>'.$title.'</a>';
}
}
I found a great module that is working with Kohana 3.3.3: https://github.com/creatoro/flexilang
So I've been trying to get data from a single item from the database using the MVC method in Joomla. I've been inspecting com_content how to do this, but I can't seem to get the id from the URL
This is my model to get the data for a single item
<?php
// No direct access to this file
defined('_JEXEC') or die('Restricted access');
// import Joomla modelitem library
jimport('joomla.application.component.modelitem');
/**
* Issuu Model
*/
class IssuuModelItem extends JModelItem
{
/**
* #var string msg
*/
protected $item;
/**
* Method to auto-populate the model state.
*
* Note. Calling getState in this method will result in recursion.
*
* #since 1.6
*
* #return void
*/
protected function populateState()
{
$app = JFactory::getApplication('site');
// Load state from the request.
$id = $app->input->getInt('id');
$this->setState('item.id', $id);
$offset = $app->input->getUInt('limitstart');
$this->setState('list.offset', $offset);
// Load the parameters.
$params = $app->getParams();
$this->setState('params', $params);
// TODO: Tune these values based on other permissions.
$user = JFactory::getUser();
if ((!$user->authorise('core.edit.state', 'com_issuu')) && (!$user->authorise('core.edit', 'com_issuu')))
{
$this->setState('filter.published', 1);
$this->setState('filter.archived', 2);
}
$this->setState('filter.language', JLanguageMultilang::isEnabled());
}
/**
* Returns a reference to the a Table object, always creating it.
*
* #param type The table type to instantiate
* #param string A prefix for the table class name. Optional.
* #param array Configuration array for model. Optional.
* #return JTable A database object
* #since 2.5
*/
public function getTable($type = 'Item', $prefix= 'IssuuTable', $config = array()) {
return JTable::getInstance($type,$prefix,$config);
}
/**
* Get the message
* #return string The message to be displayed to the user
*/
public function getItem($id = null)
{
$id = (!empty($id)) ? $id : (int) $this->getState('item.id');
if(!is_array($this->item)) {
$this->item = array();
}
// Get a db connection.
$db = JFactory::getDbo();
// Create a new query object.
$query = $db->getQuery(true);
// Select all records from the user profile table where key begins with "custom.".
// Order it by the ordering field.
$query->select($db->quoteName(array('id', 'title', 'username', 'docname', 'docid','date', 'pages', 'description')));
$query->from($db->quoteName('#__issuu_publications'));
$query->where($db->quoteName('state') . ' = `1` AND ' . $db->quoteName('id') . ' = ' . $db->qouteName($id));
$query->order('date ASC');
// Reset the query using our newly populated query object.
$db->setQuery($query);
// Load the results as a list of stdClass objects (see later for more options on retrieving data).
$this->items = $db->loadObjectList();
return $this->items;
}
}
I get a SQL error because the $id is empty.. (I removed the prefix from the table)
You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near 'ORDER BY date ASC' at line 4 SQL=SELECT `id`,`title`,`username`,`docname`,`docid`,`date`,`pages`,`description` FROM `#__issuu_publications` WHERE `state` = `1` AND `id` = ORDER BY date ASC
Any help is appreciated!
Try replacing your where clause with the following:
$query->where($db->quoteName('state') . ' = 1 AND ' . $db->quoteName('id') . ' = ' . $db->quote((int) $id));
I've removed the quotes around 1
replaced $id with (int) $id
And corrected a spelling mistake on quoteName
I've been trying to create a form in the article component backend, so that I can add few things attributes per article. I got this sample code from the joomla website documentation. http://docs.joomla.org/Adding_custom_fields_to_the_article_component
I understand the method onContentPrepareForm is an important function which adds this form in the joomla article backend. However, it doesn't appear for me. I somehow checked global other options and I got to see that the form comes up in the global article options as a seperate tab. However I'd like to add this form for each article.
The version of joomla I am using is 3.2 ...
Btw I have enabled the plugin in the backend ...
<?php
/**
* #package Joomla.Site
* #subpackage plg_content_rating
* #copyright Copyright (C) 2005 - 2012 Open Source Matters, Inc. All rights reserved.
* #license GNU General Public License version 2 or later; see LICENSE.txt
*/
defined('JPATH_BASE') or die;
jimport('joomla.utilities.date');
/**
* An example custom profile plugin.
*
* #package Joomla.Plugin
* #subpackage User.profile
* #version 1.6
*/
class plgContentRating extends JPlugin
{
/**
* Constructor
*
* #access protected
* #param object $subject The object to observe
* #param array $config An array that holds the plugin configuration
* #since 2.5
*/
public function __construct(& $subject, $config)
{
parent::__construct($subject, $config);
$this->loadLanguage();
}
/**
* #param string $context The context for the data
* #param int $data The user id
* #param object
*
* #return boolean
* #since 2.5
*/
function onContentPrepareData($context, $data)
{
if (is_object($data))
{
$articleId = isset($data->id) ? $data->id : 0;
if (!isset($data->rating) and $articleId > 0)
{
// Load the profile data from the database.
$db = JFactory::getDbo();
$query = $db->getQuery(true);
$query->select('profile_key, profile_value');
$query->from('#__user_profiles');
$query->where('user_id = ' . $db->Quote($articleId));
$query->where('profile_key LIKE ' . $db->Quote('rating.%'));
$query->order('ordering');
$db->setQuery($query);
$results = $db->loadRowList();
// Check for a database error.
if ($db->getErrorNum())
{
$this->_subject->setError($db->getErrorMsg());
return false;
}
// Merge the profile data.
$data->rating = array();
foreach ($results as $v)
{
$k = str_replace('rating.', '', $v[0]);
$data->rating[$k] = json_decode($v[1], true);
if ($data->rating[$k] === null)
{
$data->rating[$k] = $v[1];
}
}
}
}
return true;
}
/**
* #param JForm $form The form to be altered.
* #param array $data The associated data for the form.
*
* #return boolean
* #since 2.5
*/
function onContentPrepareForm($form, $data)
{
if (!($form instanceof JForm))
{
$this->_subject->setError('JERROR_NOT_A_FORM');
return false;
}
/* if (!in_array($form->getName(), array('com_content.article'))) {
return true;
}*/
// Add the extra fields to the form.
// need a seperate directory for the installer not to consider the XML a package when "discovering"
JForm::addFormPath(dirname(__FILE__) . '/rating');
$form->loadFile('rating',false);
return true;
}
/**
* Example after save content method
* Article is passed by reference, but after the save, so no changes will be saved.
* Method is called right after the content is saved
*
* #param string The context of the content passed to the plugin (added in 1.6)
* #param object A JTableContent object
* #param bool If the content is just about to be created
* #since 2.5
*/
public function onContentAfterSave($context, &$article, $isNew)
{
$articleId = $article->id;
if ($articleId && isset($article->rating) && (count($article->rating)))
{
try
{
$db = JFactory::getDbo();
$query = $db->getQuery(true);
$query->delete('#__user_profiles');
$query->where('user_id = ' . $db->Quote($articleId));
$query->where('profile_key LIKE ' . $db->Quote('rating.%'));
$db->setQuery($query);
if (!$db->query()) {
throw new Exception($db->getErrorMsg());
}
$query->clear();
$query->insert('#__user_profiles');
$order = 1;
foreach ($article->rating as $k => $v)
{
$query->values($articleId.', '.$db->quote('rating.'.$k).', '.$db->quote(json_encode($v)).', '.$order++);
}
$db->setQuery($query);
if (!$db->query()) {
throw new Exception($db->getErrorMsg());
}
}
catch (JException $e)
{
$this->_subject->setError($e->getMessage());
return false;
}
}
return true;
}
/**
* Finder after delete content method
* Article is passed by reference, but after the save, so no changes will be saved.
* Method is called right after the content is saved
*
* #param string The context of the content passed to the plugin (added in 1.6)
* #param object A JTableContent object
* #since 2.5
*/
public function onContentAfterDelete($context, $article)
{
$articleId = $article->id;
if ($articleId)
{
try
{
$db = JFactory::getDbo();
$query = $db->getQuery(true);
$query->delete();
$query->from('#__user_profiles');
$query->where('user_id = ' . $db->Quote($articleId));
$query->where('profile_key LIKE ' . $db->Quote('rating.%'));
$db->setQuery($query);
if (!$db->query())
{
throw new Exception($db->getErrorMsg());
}
}
catch (JException $e)
{
$this->_subject->setError($e->getMessage());
return false;
}
}
return true;
}
public function onContentPrepare($context, &$article, &$params, $page = 0)
{
if (!isset($article->rating) || !count($article->rating))
return;
// add extra css for table
$doc = JFactory::getDocument();
$doc->addStyleSheet(JURI::base(true).'/plugins/content/rating/rating/rating.css');
// construct a result table on the fly
jimport('joomla.html.grid');
$table = new JGrid();
// Create columns
$table->addColumn('attr')
->addColumn('value');
// populate
$rownr = 0;
foreach ($article->rating as $attr => $value) {
$table->addRow(array('class' => 'row'.($rownr % 2)));
$table->setRowCell('attr', $attr);
$table->setRowCell('value', $value);
$rownr++;
}
// wrap table in a classed <div>
$suffix = $this->params->get('ratingclass_sfx', 'rating');
$html = '<div class="'.$suffix.'">'.(string)$table.'</div>';
$article->text = $html.$article->text;
}
}
EDIT POST:
I added this code to /administrator/components/com_content/views/article/tmpl/edit.php
<?php
$i = 0;
$fieldSets = $this->form->getFieldsets();
foreach ($fieldSets as $name => $fieldSet) :
if($i <= 3){
$i++;
continue;
}
echo JHtml::_('bootstrap.addTab', 'myTab', $fieldSet->name, JText::_($fieldSet->label, true));
?>
<div class="tab-pane" id="<?php echo $name;?>">
<?php
if (isset($fieldSet->description) && !empty($fieldSet->description)) :
echo '<p class="tab-description">'.JText::_($fieldSet->description).'</p>';
endif;
foreach ($this->form->getFieldset($name) as $field):
?>
<div class="control-group">
<?php if (!$field->hidden && $name != "permissions") : ?>
<div class="control-label">
<?php echo $field->label; ?>
</div>
<?php endif; ?>
<div class="<?php if ($name != "permissions") : ?>controls<?php endif; ?>">
<?php echo $field->input; ?>
</div>
</div>
<?php
endforeach;
?>
</div>
<?php echo JHtml::_('bootstrap.endTab'); ?>
<?php endforeach; ?>
As you've mentioned the core tmpl file won't support your changes.
Hacking the core files (as you've done) is a very bad idea for several reason, including that they could be overwritten when the next 3.2.x security patch is released (like the upcoming 3.2.1) and most certainly will be when 3.5 is released. Given the rapidity Joomla releases security patches and their regular 1-click Major and Minor update cycle the last thing you want to be worrying about is your changes being blown away.
Luckily Joomla lets you create template overrides, the process for admin is pretty much the same as overrides for front-end templates.
Luckily for you the modification is in the right file, assuming you're using the default Admin template Isis simply copy
/administrator/components/com_content/views/article/tmpl/edit.php
to:
/administrator/templates/isis/html/com_content/article/edit.php
You may want to revert your original file but as mentioned it's almost certainly to get updated in either a security update or version update.
found a solution to your problem (and mine) in another article here solution to your problem hope it helps. It appears that the example plugin contains an error