Աշխատանք տվյալների բազայի հետ Drupal 7-ում - Դաս 6 - Հարցման արագ փոփոխություն (hook_query_alter)
Հարցման փոփոխում կատարման պահին
Դինամիկ ընտրության հարցումների կարևոր առանձնահատկությունն այն է, որ այլ մոդուլները կարող են փոփոխել հարցումները «թռիչքի վրա»։ Սա թույլ է տալիս այլ մոդուլներին ավելացնել իրենց հրահանգները հարցման մեջ՝ այդպիսով ազդելով դրա վարքագծի վրա կամ փոփոխություններ կիրառել կատարման պահին, օրինակ՝ սահմանել հասանելիության իրավունքներ նոդերի համար։ Կան հարցման փոփոխման երեք բաղադրիչ՝ tagging (պիտակավորում), meta data (մետա տվյալներ) և hook_query_alter()
։
Պիտակավորում (Tagging)
Ցանկացած դինամիկ ընտրության հարցում կարող է պիտակավորվել մեկ կամ մի քանի տողերով։ Այդ պիտակները ծառայում են որպես հարցման տեսակի նույնացուցիչ, ինչը հետագայում թույլ է տալիս որոշել հարցումը և ավելացնել գործողություններ։ Պիտակները պետք է լինեն թույլատրելի php փոփոխականների անունների նման՝ փոքրատառ, թվային և տառային։ Պիտակ ավելացնելու համար օգտագործեք addTag()
մեթոդը։
<?php $query->addTag('node_access'); ?>
Հարցման պիտակների ստուգման համար կան հետևյալ մեթոդները՝
<?php // Վերադարձնում է TRUE եթե հարցումն ունի տվյալ պիտակը։ $query->hasTag('example'); // Վերադարձնում է TRUE եթե հարցումն ունի բոլոր նշված պիտակները։ $query->hasAllTags('example1', 'example2'); // Վերադարձնում է TRUE եթե հարցումն ունի գոնե մեկը նշված պիտակներից։ $query->hasAnyTag('example1', 'example2'); ?>
hasAllTags()
և hasAnyTag()
մեթոդները ընդունում են երկու պարամետր՝ կարգը կարևոր չէ։ Կան նաև որոշ պատրաստի պիտակներ՝
- node_access
- Հարցման մեջ պետք է գործի նոդերի հասանելիության սահմանափակում։
- translatable
- Հարցումը վերաբերում է թարգմանելի տողերին։
- term_access
- Հարցումը վերաբերում է տերմինների հասանելիության սահմանափակումներին։
- views
- Հարցումը ստեղծվել է Views մոդուլով։
Meta data (մետա տվյալներ)
Հարցումները կարող են նաև կցել մետա տվյալներ։ Մետա տվյալներն օգնում են հարցումը փոփոխելու կատարման պահին։ Դրանք կարող են լինել ցանկացած php արժեք՝ որպես բանալի/արժեք զույգ։ Օրինակ՝
<?php $node = node_load($nid); // ... այստեղ ստեղծվում է $query օբյեկտ $query->addMetaData('node', $node); ?>
Մետա տվյալներն ինքնին չեն ազդում հարցման վրա։ Դրանք ծառայում են որպես լրացուցիչ տվյալներ, որոնք hook_query_alter()-ը կարող է օգտագործել։ Մետա տվյալներին հասնելու համար՝
<?php $node = $query->getMetaData('node'); ?>
Եթե տվյալ բանալիով մետա տվյալ չգտնվի, կվերադարձվի NULL
։
hook_query_alter()
Պիտակներն ու մետա տվյալները չեն կատարում գործողություն հարցման վրա։ Դրանք պարզապես փոխանցում են ինֆորմացիա hook_query_alter()
-ին, որը կարող է փոխել դինամիկ հարցումը։ Բոլոր դինամիկ հարցումները փոխանցվում են hook_query_alter()
-ին execute()
մեթոդի կանչից առաջ։ Սա հնարավորություն է տալիս մոդուլներին փոփոխել հարցումը ինչպես անհրաժեշտ է։ Հուկը ընդունում է մեկ պարամետր՝ հարցման օբյեկտը։
<?php /** * hook_query_alter() իրականացում։ */ function example_query_alter(QueryAlterableInterface $query) { // ... } ?>
Դուք կարող եք նաև գրել հուկ՝ ըստ պիտակի անունի։ Օրինակ՝ եթե պիտակ է node_access
, կարող եք գրել՝
<?php function example_query_node_access_alter(QueryAlterableInterface $query) { // ... } ?>
Երկու կարևոր նկատառում hook_query_alter()-ի համար
- $query-ն չի փոխանցվում հղումով։ Քանի որ դա օբյեկտ է, php5-ում այն փոխանցվում է ըստ հղման առանց հատուկ նշման։
- Պարամետրերի տիպը հստակ սահմանված է՝ QueryAlterableInterface, ինչը պաշտպանում է սխալ տիպի փոխանցումից։
hook_query_alter()
-ը կարող է ցանկացած բան անել հարցման օբյեկտի հետ, բացի այն դեպքից, երբ հարցումը կկատարվի հենց այդ հուկի ներսում՝ ինչը կհանգեցնի ռեկուրսիայի։ Օրինակ՝ դուք կարող եք՝
- Ավելացնել դաշտեր կամ միավորումներ
- Ավելացնել պայմաններ կամ having
- Փոխել
ORDER BY
- Կատարել node_access սահմանափակումներ
Հարցման մասերին հասնելու համար՝
<?php $fields =& $query->getFields(); $expressions =& $query->getExpressions(); $tables =& $query->getTables(); $order =& $query->getOrderBy(); $where =& $query->conditions(); $having =& $query->havingConditions(); ?>
Կարևոր է հիշել, որ բոլոր վերոնշյալ մեթոդները վերադարձնում են հղումներ, ուստի փոփոխությունները անմիջապես ազդում են հարցման վրա։ Այս մեթոդները հիմնականում վերադարձնում են զանգվածներ՝ կառուցվածքի մասին տեղեկատվություն կարելի է ստանալ includes/database/select.inc
ֆայլում։