Showing
40 changed files
with
2016 additions
and
0 deletions
modules/csna/.gitignore
0 → 100644
| 1 | +Thumbs.db |
modules/csna/LICENSE.txt
0 → 100644
| 1 | + GNU GENERAL PUBLIC LICENSE | ||
| 2 | + Version 2, June 1991 | ||
| 3 | + | ||
| 4 | + Copyright (C) 1989, 1991 Free Software Foundation, Inc., | ||
| 5 | + 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA | ||
| 6 | + Everyone is permitted to copy and distribute verbatim copies | ||
| 7 | + of this license document, but changing it is not allowed. | ||
| 8 | + | ||
| 9 | + Preamble | ||
| 10 | + | ||
| 11 | + The licenses for most software are designed to take away your | ||
| 12 | +freedom to share and change it. By contrast, the GNU General Public | ||
| 13 | +License is intended to guarantee your freedom to share and change free | ||
| 14 | +software--to make sure the software is free for all its users. This | ||
| 15 | +General Public License applies to most of the Free Software | ||
| 16 | +Foundation's software and to any other program whose authors commit to | ||
| 17 | +using it. (Some other Free Software Foundation software is covered by | ||
| 18 | +the GNU Lesser General Public License instead.) You can apply it to | ||
| 19 | +your programs, too. | ||
| 20 | + | ||
| 21 | + When we speak of free software, we are referring to freedom, not | ||
| 22 | +price. Our General Public Licenses are designed to make sure that you | ||
| 23 | +have the freedom to distribute copies of free software (and charge for | ||
| 24 | +this service if you wish), that you receive source code or can get it | ||
| 25 | +if you want it, that you can change the software or use pieces of it | ||
| 26 | +in new free programs; and that you know you can do these things. | ||
| 27 | + | ||
| 28 | + To protect your rights, we need to make restrictions that forbid | ||
| 29 | +anyone to deny you these rights or to ask you to surrender the rights. | ||
| 30 | +These restrictions translate to certain responsibilities for you if you | ||
| 31 | +distribute copies of the software, or if you modify it. | ||
| 32 | + | ||
| 33 | + For example, if you distribute copies of such a program, whether | ||
| 34 | +gratis or for a fee, you must give the recipients all the rights that | ||
| 35 | +you have. You must make sure that they, too, receive or can get the | ||
| 36 | +source code. And you must show them these terms so they know their | ||
| 37 | +rights. | ||
| 38 | + | ||
| 39 | + We protect your rights with two steps: (1) copyright the software, and | ||
| 40 | +(2) offer you this license which gives you legal permission to copy, | ||
| 41 | +distribute and/or modify the software. | ||
| 42 | + | ||
| 43 | + Also, for each author's protection and ours, we want to make certain | ||
| 44 | +that everyone understands that there is no warranty for this free | ||
| 45 | +software. If the software is modified by someone else and passed on, we | ||
| 46 | +want its recipients to know that what they have is not the original, so | ||
| 47 | +that any problems introduced by others will not reflect on the original | ||
| 48 | +authors' reputations. | ||
| 49 | + | ||
| 50 | + Finally, any free program is threatened constantly by software | ||
| 51 | +patents. We wish to avoid the danger that redistributors of a free | ||
| 52 | +program will individually obtain patent licenses, in effect making the | ||
| 53 | +program proprietary. To prevent this, we have made it clear that any | ||
| 54 | +patent must be licensed for everyone's free use or not licensed at all. | ||
| 55 | + | ||
| 56 | + The precise terms and conditions for copying, distribution and | ||
| 57 | +modification follow. | ||
| 58 | + | ||
| 59 | + GNU GENERAL PUBLIC LICENSE | ||
| 60 | + TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION | ||
| 61 | + | ||
| 62 | + 0. This License applies to any program or other work which contains | ||
| 63 | +a notice placed by the copyright holder saying it may be distributed | ||
| 64 | +under the terms of this General Public License. The "Program", below, | ||
| 65 | +refers to any such program or work, and a "work based on the Program" | ||
| 66 | +means either the Program or any derivative work under copyright law: | ||
| 67 | +that is to say, a work containing the Program or a portion of it, | ||
| 68 | +either verbatim or with modifications and/or translated into another | ||
| 69 | +language. (Hereinafter, translation is included without limitation in | ||
| 70 | +the term "modification".) Each licensee is addressed as "you". | ||
| 71 | + | ||
| 72 | +Activities other than copying, distribution and modification are not | ||
| 73 | +covered by this License; they are outside its scope. The act of | ||
| 74 | +running the Program is not restricted, and the output from the Program | ||
| 75 | +is covered only if its contents constitute a work based on the | ||
| 76 | +Program (independent of having been made by running the Program). | ||
| 77 | +Whether that is true depends on what the Program does. | ||
| 78 | + | ||
| 79 | + 1. You may copy and distribute verbatim copies of the Program's | ||
| 80 | +source code as you receive it, in any medium, provided that you | ||
| 81 | +conspicuously and appropriately publish on each copy an appropriate | ||
| 82 | +copyright notice and disclaimer of warranty; keep intact all the | ||
| 83 | +notices that refer to this License and to the absence of any warranty; | ||
| 84 | +and give any other recipients of the Program a copy of this License | ||
| 85 | +along with the Program. | ||
| 86 | + | ||
| 87 | +You may charge a fee for the physical act of transferring a copy, and | ||
| 88 | +you may at your option offer warranty protection in exchange for a fee. | ||
| 89 | + | ||
| 90 | + 2. You may modify your copy or copies of the Program or any portion | ||
| 91 | +of it, thus forming a work based on the Program, and copy and | ||
| 92 | +distribute such modifications or work under the terms of Section 1 | ||
| 93 | +above, provided that you also meet all of these conditions: | ||
| 94 | + | ||
| 95 | + a) You must cause the modified files to carry prominent notices | ||
| 96 | + stating that you changed the files and the date of any change. | ||
| 97 | + | ||
| 98 | + b) You must cause any work that you distribute or publish, that in | ||
| 99 | + whole or in part contains or is derived from the Program or any | ||
| 100 | + part thereof, to be licensed as a whole at no charge to all third | ||
| 101 | + parties under the terms of this License. | ||
| 102 | + | ||
| 103 | + c) If the modified program normally reads commands interactively | ||
| 104 | + when run, you must cause it, when started running for such | ||
| 105 | + interactive use in the most ordinary way, to print or display an | ||
| 106 | + announcement including an appropriate copyright notice and a | ||
| 107 | + notice that there is no warranty (or else, saying that you provide | ||
| 108 | + a warranty) and that users may redistribute the program under | ||
| 109 | + these conditions, and telling the user how to view a copy of this | ||
| 110 | + License. (Exception: if the Program itself is interactive but | ||
| 111 | + does not normally print such an announcement, your work based on | ||
| 112 | + the Program is not required to print an announcement.) | ||
| 113 | + | ||
| 114 | +These requirements apply to the modified work as a whole. If | ||
| 115 | +identifiable sections of that work are not derived from the Program, | ||
| 116 | +and can be reasonably considered independent and separate works in | ||
| 117 | +themselves, then this License, and its terms, do not apply to those | ||
| 118 | +sections when you distribute them as separate works. But when you | ||
| 119 | +distribute the same sections as part of a whole which is a work based | ||
| 120 | +on the Program, the distribution of the whole must be on the terms of | ||
| 121 | +this License, whose permissions for other licensees extend to the | ||
| 122 | +entire whole, and thus to each and every part regardless of who wrote it. | ||
| 123 | + | ||
| 124 | +Thus, it is not the intent of this section to claim rights or contest | ||
| 125 | +your rights to work written entirely by you; rather, the intent is to | ||
| 126 | +exercise the right to control the distribution of derivative or | ||
| 127 | +collective works based on the Program. | ||
| 128 | + | ||
| 129 | +In addition, mere aggregation of another work not based on the Program | ||
| 130 | +with the Program (or with a work based on the Program) on a volume of | ||
| 131 | +a storage or distribution medium does not bring the other work under | ||
| 132 | +the scope of this License. | ||
| 133 | + | ||
| 134 | + 3. You may copy and distribute the Program (or a work based on it, | ||
| 135 | +under Section 2) in object code or executable form under the terms of | ||
| 136 | +Sections 1 and 2 above provided that you also do one of the following: | ||
| 137 | + | ||
| 138 | + a) Accompany it with the complete corresponding machine-readable | ||
| 139 | + source code, which must be distributed under the terms of Sections | ||
| 140 | + 1 and 2 above on a medium customarily used for software interchange; or, | ||
| 141 | + | ||
| 142 | + b) Accompany it with a written offer, valid for at least three | ||
| 143 | + years, to give any third party, for a charge no more than your | ||
| 144 | + cost of physically performing source distribution, a complete | ||
| 145 | + machine-readable copy of the corresponding source code, to be | ||
| 146 | + distributed under the terms of Sections 1 and 2 above on a medium | ||
| 147 | + customarily used for software interchange; or, | ||
| 148 | + | ||
| 149 | + c) Accompany it with the information you received as to the offer | ||
| 150 | + to distribute corresponding source code. (This alternative is | ||
| 151 | + allowed only for noncommercial distribution and only if you | ||
| 152 | + received the program in object code or executable form with such | ||
| 153 | + an offer, in accord with Subsection b above.) | ||
| 154 | + | ||
| 155 | +The source code for a work means the preferred form of the work for | ||
| 156 | +making modifications to it. For an executable work, complete source | ||
| 157 | +code means all the source code for all modules it contains, plus any | ||
| 158 | +associated interface definition files, plus the scripts used to | ||
| 159 | +control compilation and installation of the executable. However, as a | ||
| 160 | +special exception, the source code distributed need not include | ||
| 161 | +anything that is normally distributed (in either source or binary | ||
| 162 | +form) with the major components (compiler, kernel, and so on) of the | ||
| 163 | +operating system on which the executable runs, unless that component | ||
| 164 | +itself accompanies the executable. | ||
| 165 | + | ||
| 166 | +If distribution of executable or object code is made by offering | ||
| 167 | +access to copy from a designated place, then offering equivalent | ||
| 168 | +access to copy the source code from the same place counts as | ||
| 169 | +distribution of the source code, even though third parties are not | ||
| 170 | +compelled to copy the source along with the object code. | ||
| 171 | + | ||
| 172 | + 4. You may not copy, modify, sublicense, or distribute the Program | ||
| 173 | +except as expressly provided under this License. Any attempt | ||
| 174 | +otherwise to copy, modify, sublicense or distribute the Program is | ||
| 175 | +void, and will automatically terminate your rights under this License. | ||
| 176 | +However, parties who have received copies, or rights, from you under | ||
| 177 | +this License will not have their licenses terminated so long as such | ||
| 178 | +parties remain in full compliance. | ||
| 179 | + | ||
| 180 | + 5. You are not required to accept this License, since you have not | ||
| 181 | +signed it. However, nothing else grants you permission to modify or | ||
| 182 | +distribute the Program or its derivative works. These actions are | ||
| 183 | +prohibited by law if you do not accept this License. Therefore, by | ||
| 184 | +modifying or distributing the Program (or any work based on the | ||
| 185 | +Program), you indicate your acceptance of this License to do so, and | ||
| 186 | +all its terms and conditions for copying, distributing or modifying | ||
| 187 | +the Program or works based on it. | ||
| 188 | + | ||
| 189 | + 6. Each time you redistribute the Program (or any work based on the | ||
| 190 | +Program), the recipient automatically receives a license from the | ||
| 191 | +original licensor to copy, distribute or modify the Program subject to | ||
| 192 | +these terms and conditions. You may not impose any further | ||
| 193 | +restrictions on the recipients' exercise of the rights granted herein. | ||
| 194 | +You are not responsible for enforcing compliance by third parties to | ||
| 195 | +this License. | ||
| 196 | + | ||
| 197 | + 7. If, as a consequence of a court judgment or allegation of patent | ||
| 198 | +infringement or for any other reason (not limited to patent issues), | ||
| 199 | +conditions are imposed on you (whether by court order, agreement or | ||
| 200 | +otherwise) that contradict the conditions of this License, they do not | ||
| 201 | +excuse you from the conditions of this License. If you cannot | ||
| 202 | +distribute so as to satisfy simultaneously your obligations under this | ||
| 203 | +License and any other pertinent obligations, then as a consequence you | ||
| 204 | +may not distribute the Program at all. For example, if a patent | ||
| 205 | +license would not permit royalty-free redistribution of the Program by | ||
| 206 | +all those who receive copies directly or indirectly through you, then | ||
| 207 | +the only way you could satisfy both it and this License would be to | ||
| 208 | +refrain entirely from distribution of the Program. | ||
| 209 | + | ||
| 210 | +If any portion of this section is held invalid or unenforceable under | ||
| 211 | +any particular circumstance, the balance of the section is intended to | ||
| 212 | +apply and the section as a whole is intended to apply in other | ||
| 213 | +circumstances. | ||
| 214 | + | ||
| 215 | +It is not the purpose of this section to induce you to infringe any | ||
| 216 | +patents or other property right claims or to contest validity of any | ||
| 217 | +such claims; this section has the sole purpose of protecting the | ||
| 218 | +integrity of the free software distribution system, which is | ||
| 219 | +implemented by public license practices. Many people have made | ||
| 220 | +generous contributions to the wide range of software distributed | ||
| 221 | +through that system in reliance on consistent application of that | ||
| 222 | +system; it is up to the author/donor to decide if he or she is willing | ||
| 223 | +to distribute software through any other system and a licensee cannot | ||
| 224 | +impose that choice. | ||
| 225 | + | ||
| 226 | +This section is intended to make thoroughly clear what is believed to | ||
| 227 | +be a consequence of the rest of this License. | ||
| 228 | + | ||
| 229 | + 8. If the distribution and/or use of the Program is restricted in | ||
| 230 | +certain countries either by patents or by copyrighted interfaces, the | ||
| 231 | +original copyright holder who places the Program under this License | ||
| 232 | +may add an explicit geographical distribution limitation excluding | ||
| 233 | +those countries, so that distribution is permitted only in or among | ||
| 234 | +countries not thus excluded. In such case, this License incorporates | ||
| 235 | +the limitation as if written in the body of this License. | ||
| 236 | + | ||
| 237 | + 9. The Free Software Foundation may publish revised and/or new versions | ||
| 238 | +of the General Public License from time to time. Such new versions will | ||
| 239 | +be similar in spirit to the present version, but may differ in detail to | ||
| 240 | +address new problems or concerns. | ||
| 241 | + | ||
| 242 | +Each version is given a distinguishing version number. If the Program | ||
| 243 | +specifies a version number of this License which applies to it and "any | ||
| 244 | +later version", you have the option of following the terms and conditions | ||
| 245 | +either of that version or of any later version published by the Free | ||
| 246 | +Software Foundation. If the Program does not specify a version number of | ||
| 247 | +this License, you may choose any version ever published by the Free Software | ||
| 248 | +Foundation. | ||
| 249 | + | ||
| 250 | + 10. If you wish to incorporate parts of the Program into other free | ||
| 251 | +programs whose distribution conditions are different, write to the author | ||
| 252 | +to ask for permission. For software which is copyrighted by the Free | ||
| 253 | +Software Foundation, write to the Free Software Foundation; we sometimes | ||
| 254 | +make exceptions for this. Our decision will be guided by the two goals | ||
| 255 | +of preserving the free status of all derivatives of our free software and | ||
| 256 | +of promoting the sharing and reuse of software generally. | ||
| 257 | + | ||
| 258 | + NO WARRANTY | ||
| 259 | + | ||
| 260 | + 11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY | ||
| 261 | +FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN | ||
| 262 | +OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES | ||
| 263 | +PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED | ||
| 264 | +OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF | ||
| 265 | +MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS | ||
| 266 | +TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE | ||
| 267 | +PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING, | ||
| 268 | +REPAIR OR CORRECTION. | ||
| 269 | + | ||
| 270 | + 12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING | ||
| 271 | +WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR | ||
| 272 | +REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES, | ||
| 273 | +INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING | ||
| 274 | +OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED | ||
| 275 | +TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY | ||
| 276 | +YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER | ||
| 277 | +PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE | ||
| 278 | +POSSIBILITY OF SUCH DAMAGES. | ||
| 279 | + | ||
| 280 | + END OF TERMS AND CONDITIONS | ||
| 281 | + | ||
| 282 | + How to Apply These Terms to Your New Programs | ||
| 283 | + | ||
| 284 | + If you develop a new program, and you want it to be of the greatest | ||
| 285 | +possible use to the public, the best way to achieve this is to make it | ||
| 286 | +free software which everyone can redistribute and change under these terms. | ||
| 287 | + | ||
| 288 | + To do so, attach the following notices to the program. It is safest | ||
| 289 | +to attach them to the start of each source file to most effectively | ||
| 290 | +convey the exclusion of warranty; and each file should have at least | ||
| 291 | +the "copyright" line and a pointer to where the full notice is found. | ||
| 292 | + | ||
| 293 | + <one line to give the program's name and a brief idea of what it does.> | ||
| 294 | + Copyright (C) <year> <name of author> | ||
| 295 | + | ||
| 296 | + This program is free software; you can redistribute it and/or modify | ||
| 297 | + it under the terms of the GNU General Public License as published by | ||
| 298 | + the Free Software Foundation; either version 2 of the License, or | ||
| 299 | + (at your option) any later version. | ||
| 300 | + | ||
| 301 | + This program is distributed in the hope that it will be useful, | ||
| 302 | + but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
| 303 | + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
| 304 | + GNU General Public License for more details. | ||
| 305 | + | ||
| 306 | + You should have received a copy of the GNU General Public License along | ||
| 307 | + with this program; if not, write to the Free Software Foundation, Inc., | ||
| 308 | + 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. | ||
| 309 | + | ||
| 310 | +Also add information on how to contact you by electronic and paper mail. | ||
| 311 | + | ||
| 312 | +If the program is interactive, make it output a short notice like this | ||
| 313 | +when it starts in an interactive mode: | ||
| 314 | + | ||
| 315 | + Gnomovision version 69, Copyright (C) year name of author | ||
| 316 | + Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'. | ||
| 317 | + This is free software, and you are welcome to redistribute it | ||
| 318 | + under certain conditions; type `show c' for details. | ||
| 319 | + | ||
| 320 | +The hypothetical commands `show w' and `show c' should show the appropriate | ||
| 321 | +parts of the General Public License. Of course, the commands you use may | ||
| 322 | +be called something other than `show w' and `show c'; they could even be | ||
| 323 | +mouse-clicks or menu items--whatever suits your program. | ||
| 324 | + | ||
| 325 | +You should also get your employer (if you work as a programmer) or your | ||
| 326 | +school, if any, to sign a "copyright disclaimer" for the program, if | ||
| 327 | +necessary. Here is a sample; alter the names: | ||
| 328 | + | ||
| 329 | + Yoyodyne, Inc., hereby disclaims all copyright interest in the program | ||
| 330 | + `Gnomovision' (which makes passes at compilers) written by James Hacker. | ||
| 331 | + | ||
| 332 | + <signature of Ty Coon>, 1 April 1989 | ||
| 333 | + Ty Coon, President of Vice | ||
| 334 | + | ||
| 335 | +This General Public License does not permit incorporating your program into | ||
| 336 | +proprietary programs. If your program is a subroutine library, you may | ||
| 337 | +consider it more useful to permit linking proprietary applications with the | ||
| 338 | +library. If this is what you want to do, use the GNU Lesser General | ||
| 339 | +Public License instead of this License. |
modules/csna/README.txt
0 → 100644
| 1 | +This module provides avalibility to allow user sign in with top Chinese Social | ||
| 2 | +Networks. | ||
| 3 | + | ||
| 4 | +Currently we support: | ||
| 5 | +Sina weibo (新浪微博), Chinese twitter like website. | ||
| 6 | +Tencent (QQ), biggest Chinese IM provider. | ||
| 7 | +Renren(人人网), biggest Chinese facebook like website. | ||
| 8 | +Kaixin001(开心网), secondary Chinese facebook like website. | ||
| 9 | + | ||
| 10 | +Configuration: | ||
| 11 | +The module contians 1 main module and 4 sub-modules. | ||
| 12 | +Each of these 4 sub-modules represent 4 Chinese Social Networks. | ||
| 13 | +Install and enable main module and any of these sub-modules you desired. | ||
| 14 | +Go to configuration page (/admin/config/csna) and fill the KEY and SECRET you | ||
| 15 | +get from these Chinese Social Networks. | ||
| 16 | + | ||
| 17 | +URL of subscribing for KEYs and SECRETs: | ||
| 18 | +Weibo http://open.weibo.com/ | ||
| 19 | +QQ http://connect.qq.com/ | ||
| 20 | +Renren http://dev.renren.com/website | ||
| 21 | +Kaixin http://open.kaixin001.com/ |
modules/csna/csna.admin.inc
0 → 100644
| 1 | +<?php | ||
| 2 | + | ||
| 3 | +/** | ||
| 4 | + * @file | ||
| 5 | + * Functionality for CSNA administration. | ||
| 6 | + */ | ||
| 7 | + | ||
| 8 | +/** | ||
| 9 | + * Menu callback: CSNA key or secrect config. | ||
| 10 | + */ | ||
| 11 | +function csna_admin_settings() { | ||
| 12 | + $providers = csna_providers(); | ||
| 13 | + foreach ($providers as $provider_id => $provider) { | ||
| 14 | + $form[$provider_id] = array( | ||
| 15 | + '#type' => 'fieldset', | ||
| 16 | + '#title' => $provider['title'], | ||
| 17 | + '#description' => $provider['description'], | ||
| 18 | + ); | ||
| 19 | + $form[$provider_id]['csna_' . $provider_id . '_key'] = array( | ||
| 20 | + '#type' => 'textfield', | ||
| 21 | + '#title' => t('Key'), | ||
| 22 | + '#size' => 40, | ||
| 23 | + '#maxlength' => 255, | ||
| 24 | + '#default_value' => variable_get('csna_' . $provider_id . '_key', ''), | ||
| 25 | + ); | ||
| 26 | + $form[$provider_id]['csna_' . $provider_id . '_secret'] = array( | ||
| 27 | + '#type' => 'textfield', | ||
| 28 | + '#title' => t('Secret'), | ||
| 29 | + '#size' => 40, | ||
| 30 | + '#maxlength' => 255, | ||
| 31 | + '#default_value' => variable_get('csna_' . $provider_id . '_secret', ''), | ||
| 32 | + ); | ||
| 33 | + } | ||
| 34 | + | ||
| 35 | + // If no provider/sub-module was found, provide a default help text. | ||
| 36 | + if (!isset($form)) { | ||
| 37 | + $form['default_message'] = array( | ||
| 38 | + '#markup' => t('<strong>No CSNA third party API provider module has been enabled yet</strong>.<br/>Please enable <strong>at least a CSNA sub-module</strong> or any other <strong>CSNA API provider</strong> from the !modadminlink then feel free to browse this page again.<br/>See more information on !projectlink about <strong>supported providers</strong> and <strong>installation instructions</strong>.', array( | ||
| 39 | + '!modadminlink' => l(t('module administration page'), 'admin/modules'), | ||
| 40 | + '!projectlink' => l(t("module project's page"), 'http://drupal.org/project/csna', array('attributes' => array('target' => '_blank'))), | ||
| 41 | + )), | ||
| 42 | + ); | ||
| 43 | + return $form; | ||
| 44 | + } | ||
| 45 | + else { | ||
| 46 | + $form['csna_require_email'] = array( | ||
| 47 | + '#type' => 'checkbox', | ||
| 48 | + '#title' => t('Require email'), | ||
| 49 | + '#description' => t('Require user entering email after successful user login if email hasn\'t been set yet.'), | ||
| 50 | + '#default_value' => variable_get('csna_require_email', TRUE), | ||
| 51 | + ); | ||
| 52 | + | ||
| 53 | + return system_settings_form($form); | ||
| 54 | + } | ||
| 55 | +} |
modules/csna/csna.api.php
0 → 100644
| 1 | +<?php | ||
| 2 | +/** | ||
| 3 | + * @file | ||
| 4 | + * API documentation for the Chinese Social Networks Authentication module. | ||
| 5 | + */ | ||
| 6 | + | ||
| 7 | +/** | ||
| 8 | + * Define Authentication providers available to the CSNA framework. | ||
| 9 | + * | ||
| 10 | + * The Chinese Social Networks Authentication (CSNA) module uses this hook to | ||
| 11 | + * gather information on provider authentication methods defined by enabled | ||
| 12 | + * modules. These methods depend on a variety of properties used by CSNA to | ||
| 13 | + * integrate with third party API providers based on the OAuth protocol. | ||
| 14 | + * | ||
| 15 | + * By default CSNA supports the following Authentication API providers through | ||
| 16 | + * sub-modules: | ||
| 17 | + * - Sina weibo (新浪微博), Chinese twitter like website. | ||
| 18 | + * - Tencent (QQ), biggest Chinese IM provider. | ||
| 19 | + * - Renren(人人网), biggest Chinese facebook like website. | ||
| 20 | + * - Kaixin001(开心网), secondary Chinese facebook like website. | ||
| 21 | + * | ||
| 22 | + * This hook allows other modules to define custom authentication third party | ||
| 23 | + * API providers by defining all the necessary information for CSNA's | ||
| 24 | + * implementation of the OAuth protocol. | ||
| 25 | + * | ||
| 26 | + * @return array | ||
| 27 | + * An array of providers keyed by provider_id with the following properties: | ||
| 28 | + * - title: The title or name of the defined provider. | ||
| 29 | + * - description: Description text to appear on the admin page for the | ||
| 30 | + * configuration of the required parameters for this specific provider, | ||
| 31 | + * such as Authentication API KEY or Password. | ||
| 32 | + * - display_title: The title to be displayed in the list of links of | ||
| 33 | + * providers returned by theme_csna_providers, which displays in the user | ||
| 34 | + * login/registration forms and block. For better usage, HTML is allowed | ||
| 35 | + * for this property, for example to display an image or logo. | ||
| 36 | + * - type: string identifying the type of OAuth protocol used. By default, | ||
| 37 | + * CSNA provides a constant for 'oauth2', see CSNA_OAUTH2, but any other | ||
| 38 | + * custom OAuth type could also be used and provided for this property. | ||
| 39 | + * - authorize_uri: The URL used by providers to authenticate users through | ||
| 40 | + * the OAuth protocol. | ||
| 41 | + * - access_token_uri: The URL used by CSNA to get the authentication token | ||
| 42 | + * returned by providers if operation was successful. | ||
| 43 | + * - info_uri: This URL allows capturing User's information from third party | ||
| 44 | + * authentication providers, such as username, or other useful information. | ||
| 45 | + * | ||
| 46 | + * @see csna_providers() | ||
| 47 | + * @see csna_weibo_csna_provider_info() | ||
| 48 | + */ | ||
| 49 | +function hook_csna_provider_info() { | ||
| 50 | + // Example taken from the csna_weibo sub-module. | ||
| 51 | + $providers = array(); | ||
| 52 | + | ||
| 53 | + $providers['weibo'] = array( | ||
| 54 | + 'title' => t('Weibo Sina'), | ||
| 55 | + 'description' => t('Set your Sina Weibo authorized KEY and SECRET below.'), | ||
| 56 | + 'display_title' => csna_get_weibo_button_image(), | ||
| 57 | + 'type' => CSNA_OAUTH2, | ||
| 58 | + 'authorize_uri' => 'https://api.weibo.com/oauth2/authorize', | ||
| 59 | + 'access_token_uri' => 'https://api.weibo.com/oauth2/access_token', | ||
| 60 | + 'info_uri' => 'https://api.weibo.com/2/users/show.json', | ||
| 61 | + ); | ||
| 62 | + | ||
| 63 | + return $providers; | ||
| 64 | +} | ||
| 65 | + | ||
| 66 | +/** | ||
| 67 | + * Allows other modules to alter already defined list of providers. | ||
| 68 | + * | ||
| 69 | + * Any of the providers and any of their properties or values can be modified | ||
| 70 | + * by using an implementation of this hook. | ||
| 71 | + * | ||
| 72 | + * @param array $providers | ||
| 73 | + * An associative array of providers keyed by the provider_id, as returned by | ||
| 74 | + * the function csna_providers(). See hook_csna_provider_info for a detailed | ||
| 75 | + * list of all the defined and required properties for each provider. | ||
| 76 | + * | ||
| 77 | + * @see hook_csna_provider_info() | ||
| 78 | + * @see csna_providers() | ||
| 79 | + */ | ||
| 80 | +function hook_csna_provider_info_alter(&$providers) { | ||
| 81 | + if (isset($providers['weibo'])) { | ||
| 82 | + $providers['weibo']['display_title'] = t("Login or register with your Sina Weibo account!"); | ||
| 83 | + } | ||
| 84 | +} | ||
| 85 | + | ||
| 86 | +/** | ||
| 87 | + * Define providers custom authentication callback methods. | ||
| 88 | + * | ||
| 89 | + * The implementation of this hook is usually required when defining a Third | ||
| 90 | + * Party authentication OAuth API provider through hook_csna_provider_info. | ||
| 91 | + * | ||
| 92 | + * This hook callback is executed when returning from provider's API | ||
| 93 | + * authentication pages, with information about the operation, such as whether | ||
| 94 | + * it was successful or not. In case of success, most providers will return a | ||
| 95 | + * token or code that can be further used to verify or obtain user's | ||
| 96 | + * information through the $provider['info_uri'] defined URL. | ||
| 97 | + * | ||
| 98 | + * @param array $provider | ||
| 99 | + * An array of properties for the corresponding provider defined through | ||
| 100 | + * hook_csna_provider_info, see API hooks documentation for more information. | ||
| 101 | + * @param array $request | ||
| 102 | + * A PHP predefined variable for HTTP Request variables: $_REQUEST, received | ||
| 103 | + * from the third party authentication provider. | ||
| 104 | + * | ||
| 105 | + * @return array | ||
| 106 | + * An array of properties including the following keys and values: | ||
| 107 | + * - access_token: The access token returned by the provider through its | ||
| 108 | + * access_token_uri URL to provider further access to user's information if | ||
| 109 | + * authentication was successful. | ||
| 110 | + * - uid: The ID of the user returned from the provider used to load user | ||
| 111 | + * account through user_external_load (see core API). | ||
| 112 | + * - name: The user name returned from the provider used to load user account | ||
| 113 | + * account through user_load_by_name (see core API). | ||
| 114 | + * | ||
| 115 | + * @see csna_callback() | ||
| 116 | + * @see csna_kaixin_csna_provider_callback() | ||
| 117 | + */ | ||
| 118 | +function hook_csna_provider_callback($provider, $request) { | ||
| 119 | + // Example taken from the csna_kaixin sub-module. | ||
| 120 | + if (isset($request['code'])) { | ||
| 121 | + $parameters = array( | ||
| 122 | + 'client_id' => $provider['key'], | ||
| 123 | + 'client_secret' => $provider['secret'], | ||
| 124 | + 'grant_type' => 'authorization_code', | ||
| 125 | + 'redirect_uri' => $provider['callback'], | ||
| 126 | + 'code' => $request['code'], | ||
| 127 | + ); | ||
| 128 | + $http = drupal_http_request(url($provider['access_token_uri'], array('query' => $parameters))); | ||
| 129 | + $data = json_decode($http->data); | ||
| 130 | + $http = drupal_http_request(url($provider['info_uri'], array('query' => array('access_token' => $data->access_token)))); | ||
| 131 | + $info = json_decode($http->data); | ||
| 132 | + if (!isset($info->uid)) { | ||
| 133 | + return FALSE; | ||
| 134 | + } | ||
| 135 | + return array( | ||
| 136 | + 'access_token' => $data->access_token, | ||
| 137 | + 'uid' => $info->uid, | ||
| 138 | + 'name' => $info->name, | ||
| 139 | + ); | ||
| 140 | + } | ||
| 141 | +} |
modules/csna/csna.info
0 → 100644
| 1 | +name = CSNA | ||
| 2 | +description = Authentication for Chinese Social Networks | ||
| 3 | +package = Authentication | ||
| 4 | +core = 7.x | ||
| 5 | +configure = admin/config/services/csna | ||
| 6 | + | ||
| 7 | +; Information added by Drupal.org packaging script on 2015-10-19 | ||
| 8 | +version = "7.x-1.3" | ||
| 9 | +core = "7.x" | ||
| 10 | +project = "csna" | ||
| 11 | +datestamp = "1445231940" | ||
| 12 | + |
modules/csna/csna.module
0 → 100644
| 1 | +<?php | ||
| 2 | + | ||
| 3 | +/** | ||
| 4 | + * @file | ||
| 5 | + * The Chinese Social Networks Authentication (CSNA) module provides a global | ||
| 6 | + * framework and API to allow other modules to define specific authentication | ||
| 7 | + * methods from Chinese Social Networks through a supported OAuth protocol. | ||
| 8 | + */ | ||
| 9 | + | ||
| 10 | +define('CSNA_OAUTH2', 'oauth2'); | ||
| 11 | + | ||
| 12 | +/** | ||
| 13 | + * Implements hook_menu(). | ||
| 14 | + */ | ||
| 15 | +function csna_menu() { | ||
| 16 | + $items['csna/%csna_provider'] = array( | ||
| 17 | + 'title' => 'CSNA Redirect', | ||
| 18 | + 'page callback' => 'csna_redirect', | ||
| 19 | + 'page arguments' => array(1), | ||
| 20 | + 'access callback' => 'user_is_anonymous', | ||
| 21 | + 'type' => MENU_CALLBACK, | ||
| 22 | + ); | ||
| 23 | + | ||
| 24 | + $items['csna/%csna_provider/callback'] = array( | ||
| 25 | + 'title' => 'Authentication callback', | ||
| 26 | + 'page callback' => 'csna_callback', | ||
| 27 | + 'page arguments' => array(1), | ||
| 28 | + 'access callback' => 'user_is_anonymous', | ||
| 29 | + 'type' => MENU_CALLBACK, | ||
| 30 | + ); | ||
| 31 | + | ||
| 32 | + $items['csna/%user/complete-register'] = array( | ||
| 33 | + 'title' => t('Complete register'), | ||
| 34 | + 'page callback' => 'drupal_get_form', | ||
| 35 | + 'page arguments' => array('csna_complete_register_form', 1), | ||
| 36 | + 'access callback' => 'csna_user_edit_access', | ||
| 37 | + 'access arguments' => array(1), | ||
| 38 | + 'file' => 'csna.pages.inc', | ||
| 39 | + ); | ||
| 40 | + | ||
| 41 | + $items['admin/config/services/csna'] = array( | ||
| 42 | + 'title' => 'Chinese Social Networks Authentication settings (CSNA)', | ||
| 43 | + 'description' => 'Configure the CSNA key or secrect code settings for third party authentication API providers.', | ||
| 44 | + 'page callback' => 'drupal_get_form', | ||
| 45 | + 'page arguments' => array('csna_admin_settings'), | ||
| 46 | + 'access arguments' => array('administer csna'), | ||
| 47 | + 'file' => 'csna.admin.inc', | ||
| 48 | + ); | ||
| 49 | + | ||
| 50 | + return $items; | ||
| 51 | +} | ||
| 52 | + | ||
| 53 | +/** | ||
| 54 | + * Check the Provider ID. | ||
| 55 | + * | ||
| 56 | + * @param string $provider_id | ||
| 57 | + * The Provider ID. | ||
| 58 | + * | ||
| 59 | + * @return mixed | ||
| 60 | + * A value of $providers[$provider_id] from csna_providers(), | ||
| 61 | + * or FALSE if the value does not exist. | ||
| 62 | + */ | ||
| 63 | +function csna_provider_load($provider_id) { | ||
| 64 | + $providers = csna_providers(); | ||
| 65 | + return isset($providers[$provider_id]) ? $providers[$provider_id] : FALSE; | ||
| 66 | +} | ||
| 67 | + | ||
| 68 | +/** | ||
| 69 | + * Implements hook_perm(). | ||
| 70 | + */ | ||
| 71 | +function csna_permission() { | ||
| 72 | + return array( | ||
| 73 | + 'administer csna' => array( | ||
| 74 | + 'title' => t('Administer CSNA'), | ||
| 75 | + 'description' => t('Perform administration tasks for CSNA.'), | ||
| 76 | + ), | ||
| 77 | + ); | ||
| 78 | +} | ||
| 79 | + | ||
| 80 | +/** | ||
| 81 | + * Implements hook_theme(). | ||
| 82 | + */ | ||
| 83 | +function csna_theme($existing, $type, $theme, $path) { | ||
| 84 | + $providers = csna_providers(); | ||
| 85 | + return array( | ||
| 86 | + 'csna_providers' => array( | ||
| 87 | + 'variables' => array('providers' => $providers), | ||
| 88 | + ), | ||
| 89 | + ); | ||
| 90 | +} | ||
| 91 | + | ||
| 92 | +/** | ||
| 93 | + * Menu callback: CSNA Redirect. | ||
| 94 | + */ | ||
| 95 | +function csna_redirect($provider) { | ||
| 96 | + $parameters = array( | ||
| 97 | + 'client_id' => $provider['key'], | ||
| 98 | + 'redirect_uri' => $provider['callback'], | ||
| 99 | + 'response_type' => 'code', | ||
| 100 | + ); | ||
| 101 | + if ($provider['provider_id'] == 'wechat') { | ||
| 102 | + unset($parameters['client_id']); | ||
| 103 | + $parameters['appid'] = $provider['key']; | ||
| 104 | + $parameters['scope'] = 'snsapi_login'; | ||
| 105 | + } | ||
| 106 | + drupal_goto($provider['authorize_uri'], array('query' => $parameters)); | ||
| 107 | +} | ||
| 108 | + | ||
| 109 | +/** | ||
| 110 | + * Menu callback: CSNA Callback. | ||
| 111 | + */ | ||
| 112 | +function csna_callback($provider) { | ||
| 113 | + | ||
| 114 | + global $user; | ||
| 115 | + $data = module_invoke($provider['module'], 'csna_provider_callback', $provider, $_REQUEST); | ||
| 116 | + | ||
| 117 | + // Forcing array format because of Sina weibo will return an Object. | ||
| 118 | + if (!is_array($data)) { | ||
| 119 | + $data = (array) $data; | ||
| 120 | + } | ||
| 121 | + | ||
| 122 | + if (isset($data['access_token'])) { | ||
| 123 | + $identity = $provider['provider_id'] . '_' . $data['uid']; | ||
| 124 | + $account = user_external_load($identity); | ||
| 125 | + | ||
| 126 | + if (!isset($account->uid)) { | ||
| 127 | + $name = $data['name']; | ||
| 128 | + $ac = user_load_by_name($name); | ||
| 129 | + if ($ac) { | ||
| 130 | + $separator = '_'; | ||
| 131 | + $i = 0; | ||
| 132 | + do { | ||
| 133 | + $i++; | ||
| 134 | + $name = $data['name'] . $separator . $i; | ||
| 135 | + } while (user_load_by_name($name)); | ||
| 136 | + } | ||
| 137 | + //User avatar | ||
| 138 | + if (isset($data['avatar_link'])) { | ||
| 139 | + $avatar_directory = file_default_scheme() . '://' . variable_get('user_picture_path', 'pictures'); | ||
| 140 | + $avatar = system_retrieve_file($data['avatar_link'], $avatar_directory, TRUE, FILE_EXISTS_RENAME); | ||
| 141 | + } | ||
| 142 | + $edit = array( | ||
| 143 | + 'name' => $name, | ||
| 144 | + 'status' => 1, | ||
| 145 | + 'picture' => isset($avatar->fid) ? $avatar->fid : '', | ||
| 146 | + ); | ||
| 147 | + $account = user_save(NULL, $edit); | ||
| 148 | + user_set_authmaps($account, array('authname_csna' => $identity)); | ||
| 149 | + } | ||
| 150 | + | ||
| 151 | + csna_execute_user_login($account); | ||
| 152 | + | ||
| 153 | + if (variable_get('csna_require_email', TRUE) && empty($account->mail)) { | ||
| 154 | + drupal_goto('csna/' . $account->uid . '/complete-register'); | ||
| 155 | + } | ||
| 156 | + } | ||
| 157 | + drupal_goto('user'); | ||
| 158 | +} | ||
| 159 | + | ||
| 160 | +/** | ||
| 161 | + * Helper function for CSNA Callback. | ||
| 162 | + * | ||
| 163 | + * It executes user login after returning from provider's authentication page. | ||
| 164 | + * If no valid account is found or authentication with providers failed, this | ||
| 165 | + * function returns FALSE. | ||
| 166 | + */ | ||
| 167 | +function csna_execute_user_login($account) { | ||
| 168 | + if (empty($account) OR !isset($account->uid)) { | ||
| 169 | + return FALSE; | ||
| 170 | + } | ||
| 171 | + $form_state['uid'] = $account->uid; | ||
| 172 | + user_login_submit(array(), $form_state); | ||
| 173 | + return TRUE; | ||
| 174 | +} | ||
| 175 | + | ||
| 176 | +/** | ||
| 177 | + * Implements hook_form_alter(). | ||
| 178 | + */ | ||
| 179 | +function csna_form_alter(&$form, &$form_state, $form_id) { | ||
| 180 | + if ($form_id == 'user_login' || $form_id == 'user_login_block' || $form_id == 'user_register_form') { | ||
| 181 | + $providers = csna_providers(); | ||
| 182 | + | ||
| 183 | + // if admin form | ||
| 184 | + if (empty($form['administer_users']['#value'])) { | ||
| 185 | + if (isset($form['submitted']['user_login_block']['#suffix']) && !empty($form['submitted']['user_login_block']['#suffix'])) { | ||
| 186 | + $form['submitted']['user_login_block']['#suffix'] .= theme('csna_providers', array('providers' => $providers)); | ||
| 187 | + } | ||
| 188 | + else { | ||
| 189 | + $form['submitted']['user_login_block']['#suffix'] = theme('csna_providers', array('providers' => $providers)); | ||
| 190 | + } | ||
| 191 | + } | ||
| 192 | + } | ||
| 193 | +} | ||
| 194 | + | ||
| 195 | +/** | ||
| 196 | + * Returns an array of OAuth Third Party authentication providers. | ||
| 197 | + * | ||
| 198 | + * CSNA's API Framework provides a method for any enabled module to define | ||
| 199 | + * additional authentication providers. This function gathers information on | ||
| 200 | + * provider authentication methods defined by enabled modules. | ||
| 201 | + * | ||
| 202 | + * @return array | ||
| 203 | + * An associative array of providers keyed by the provider_id. | ||
| 204 | + * | ||
| 205 | + * @see hook_csna_provider_info() | ||
| 206 | + */ | ||
| 207 | +function csna_providers($valid = FALSE) { | ||
| 208 | + static $providers; | ||
| 209 | + | ||
| 210 | + if (!isset($providers)) { | ||
| 211 | + $providers = array(); | ||
| 212 | + | ||
| 213 | + // Build the providers array, including module names for the purpose | ||
| 214 | + // of including files if necessary. | ||
| 215 | + // An associative array of providers objects keyed by the provider_id. | ||
| 216 | + foreach (module_implements('csna_provider_info') as $module) { | ||
| 217 | + foreach (module_invoke($module, 'csna_provider_info') as $provider_id => $provider) { | ||
| 218 | + $provider['provider_id'] = $provider_id; | ||
| 219 | + $provider['module'] = $module; | ||
| 220 | + $provider['key'] = variable_get('csna_' . $provider_id . '_key', ''); | ||
| 221 | + $provider['secret'] = variable_get('csna_' . $provider_id . '_secret', ''); | ||
| 222 | + $providers[$provider_id] = $provider; | ||
| 223 | + if ($valid && (empty($provider['key']) || empty($provider['secret']))) { | ||
| 224 | + unset($providers[$provider_id]); | ||
| 225 | + } | ||
| 226 | + } | ||
| 227 | + } | ||
| 228 | + | ||
| 229 | + drupal_alter('csna_provider_info', $providers); | ||
| 230 | + | ||
| 231 | + foreach ($providers as $provider_id => & $provider) { | ||
| 232 | + $defaults = array( | ||
| 233 | + 'provider_id' => $provider_id, | ||
| 234 | + 'base' => $provider_id, | ||
| 235 | + 'title' => '', | ||
| 236 | + 'description' => '', | ||
| 237 | + 'active' => FALSE, | ||
| 238 | + 'callback' => url('csna/' . $provider_id . '/callback', array('absolute' => TRUE)), | ||
| 239 | + 'file' => '', | ||
| 240 | + ); | ||
| 241 | + | ||
| 242 | + $provider += $defaults; | ||
| 243 | + | ||
| 244 | + // Default the display title to the title if necessary. The display | ||
| 245 | + // title is used in instances where the login method has an official | ||
| 246 | + // name but a different method of display on selection forms (like some | ||
| 247 | + // text and a set of images). | ||
| 248 | + if (empty($provider['display_title'])) { | ||
| 249 | + $provider['display_title'] = $provider['title']; | ||
| 250 | + } | ||
| 251 | + | ||
| 252 | + // Default the short title to the title if necessary. Like the display | ||
| 253 | + // title, the short title is an alternate way of displaying the title to | ||
| 254 | + // the user consisting of plain text but with unnecessary information | ||
| 255 | + // stripped off. | ||
| 256 | + if (empty($provider[$provider_id]['short_title'])) { | ||
| 257 | + $provider['short_title'] = $provider['title']; | ||
| 258 | + } | ||
| 259 | + } | ||
| 260 | + } | ||
| 261 | + | ||
| 262 | + return $providers; | ||
| 263 | +} | ||
| 264 | + | ||
| 265 | +/** | ||
| 266 | + * Render a themed list of links to providers authorized login URL pages. | ||
| 267 | + * | ||
| 268 | + * @param array $providers | ||
| 269 | + * An associative array of providers keyed by the provider_id, as returned by | ||
| 270 | + * the function csna_providers(). | ||
| 271 | + * Mostly the display_title property of providers is used in this function | ||
| 272 | + * to display a custom title, name or even HTML to be linked to corresponding | ||
| 273 | + * provider's authorized login URL page. See API documentation for more | ||
| 274 | + * information on providers available properties. | ||
| 275 | + * | ||
| 276 | + * @see csna_providers() | ||
| 277 | + * @see hook_csna_provider_info() | ||
| 278 | + */ | ||
| 279 | +function theme_csna_providers($vars) { | ||
| 280 | + $providers = $vars['providers']; | ||
| 281 | + $items = array(); | ||
| 282 | + foreach ($providers as $provider_id => $provider) { | ||
| 283 | + $items[] = array( | ||
| 284 | + 'data' => l($provider['display_title'], 'csna/' . $provider_id, array('html' => TRUE)), | ||
| 285 | + 'id' => 'csna_provider_' . $provider_id, | ||
| 286 | + ); | ||
| 287 | + } | ||
| 288 | + | ||
| 289 | + return theme('item_list', array('items' => $items, 'attributes' => array('class' => 'csna-items'))); | ||
| 290 | +} | ||
| 291 | + | ||
| 292 | +/** | ||
| 293 | + * Access callback for CSNA complete register. | ||
| 294 | + * | ||
| 295 | + * @param $account | ||
| 296 | + */ | ||
| 297 | +function csna_user_edit_access($account) { | ||
| 298 | + return $GLOBALS['user']->uid == $account->uid; | ||
| 299 | +} |
modules/csna/csna.pages.inc
0 → 100644
| 1 | +<?php | ||
| 2 | + | ||
| 3 | +/** | ||
| 4 | + * @file | ||
| 5 | + * Menu callbacks for the CSNA module. | ||
| 6 | + */ | ||
| 7 | + | ||
| 8 | +/** | ||
| 9 | + * Menu callback: Set email address and password after successful user login | ||
| 10 | + */ | ||
| 11 | +function csna_complete_register_form($form, &$form_state, $account) { | ||
| 12 | + global $user; | ||
| 13 | + | ||
| 14 | + if ($account->mail) { | ||
| 15 | + drupal_goto('user'); | ||
| 16 | + } | ||
| 17 | + | ||
| 18 | + $form_state['user'] = $account; | ||
| 19 | + | ||
| 20 | + $form['mail'] = array( | ||
| 21 | + '#type' => 'textfield', | ||
| 22 | + '#title' => t('E-mail address'), | ||
| 23 | + '#maxlength' => EMAIL_MAX_LENGTH, | ||
| 24 | + '#description' => t('A valid e-mail address. All e-mails from the system will be sent to this address. The e-mail address is not made public and will only be used if you wish to receive a new password or wish to receive certain news or notifications by e-mail.'), | ||
| 25 | + '#required' => TRUE, | ||
| 26 | + ); | ||
| 27 | + | ||
| 28 | + $form['pass'] = array( | ||
| 29 | + '#type' => 'password_confirm', | ||
| 30 | + '#size' => 25, | ||
| 31 | + '#description' => t('Provide a password for the new account in both fields.'), | ||
| 32 | + '#required' => TRUE, | ||
| 33 | + ); | ||
| 34 | + | ||
| 35 | + $form['submit'] = array( | ||
| 36 | + '#type' => 'submit', | ||
| 37 | + '#value' => t('Save'), | ||
| 38 | + ); | ||
| 39 | + | ||
| 40 | + return $form; | ||
| 41 | +} | ||
| 42 | + | ||
| 43 | +function csna_complete_register_form_validate($form, &$form_state) { | ||
| 44 | + $account = $form_state['user']; | ||
| 45 | + | ||
| 46 | + // Trim whitespace from mail, to prevent confusing 'e-mail not valid' | ||
| 47 | + // warnings often caused by cutting and pasting. | ||
| 48 | + $mail = trim($form_state['values']['mail']); | ||
| 49 | + form_set_value($form['mail'], $mail, $form_state); | ||
| 50 | + | ||
| 51 | + // Validate the e-mail address, and check if it is taken by an existing user. | ||
| 52 | + if ($error = user_validate_mail($form_state['values']['mail'])) { | ||
| 53 | + form_set_error('mail', $error); | ||
| 54 | + } | ||
| 55 | + elseif ((bool) db_select('users')->fields('users', array('uid'))->condition('uid', $account->uid, '<>')->condition('mail', db_like($form_state['values']['mail']), 'LIKE')->range(0, 1)->execute()->fetchField()) { | ||
| 56 | + form_set_error('mail', t('The e-mail address %email is already taken.', array('%email' => $form_state['values']['mail']))); | ||
| 57 | + } | ||
| 58 | +} | ||
| 59 | + | ||
| 60 | +function csna_complete_register_form_submit($form, &$form_state) { | ||
| 61 | + $account = $form_state['user']; | ||
| 62 | + | ||
| 63 | + $edit = array( | ||
| 64 | + 'mail' => $form_state['values']['mail'], | ||
| 65 | + 'pass' => $form_state['values']['pass'], | ||
| 66 | + ); | ||
| 67 | + | ||
| 68 | + user_save($account, $edit); | ||
| 69 | +} | ||
| 70 | + |
modules/csna/kaixin/csna_kaixin.info
0 → 100644
| 1 | +name = CSNA Kaixin | ||
| 2 | +description = Provide authentication integration for Kaixin. | ||
| 3 | +package = Authentication | ||
| 4 | +core = 7.x | ||
| 5 | +dependencies[] = csna | ||
| 6 | +configure = admin/config/services/csna | ||
| 7 | + | ||
| 8 | +; Information added by Drupal.org packaging script on 2015-10-19 | ||
| 9 | +version = "7.x-1.3" | ||
| 10 | +core = "7.x" | ||
| 11 | +project = "csna" | ||
| 12 | +datestamp = "1445231940" | ||
| 13 | + |
modules/csna/kaixin/csna_kaixin.install
0 → 100644
modules/csna/kaixin/csna_kaixin.module
0 → 100644
| 1 | +<?php | ||
| 2 | + | ||
| 3 | +/** | ||
| 4 | + * @file | ||
| 5 | + * The CSNA Kaixin module is a sub-module of the Chinese Social Networks | ||
| 6 | + * Authentication (CSNA) framework allowing integration with the Kaixin OAuth | ||
| 7 | + * protocol for Authentication/Login. | ||
| 8 | + */ | ||
| 9 | + | ||
| 10 | +/** | ||
| 11 | + * Implements hook_csna_provider_info(). | ||
| 12 | + */ | ||
| 13 | +function csna_kaixin_csna_provider_info() { | ||
| 14 | + $providers = array(); | ||
| 15 | + $providers['kaixin'] = array( | ||
| 16 | + 'title' => t('Kaixin'), | ||
| 17 | + 'description' => t('Set your <strong>Kaixin authorized KEY</strong> and <strong>SECRET</strong> below.<br/>If you want to use an API key, you can get one at the !keylink.', array('!keylink' => l(t('Kaixin API website'), 'http://open.kaixin001.com/', array('attributes' => array('target' => '_blank'))))), | ||
| 18 | + 'display_title' => csna_get_kaixin_button_image(), | ||
| 19 | + 'authorize_uri' => 'http://api.kaixin001.com/oauth2/authorize', | ||
| 20 | + 'access_token_uri' => 'http://api.kaixin001.com/oauth2/access_token', | ||
| 21 | + 'info_uri' => 'https://api.kaixin001.com/users/me.json', | ||
| 22 | + ); | ||
| 23 | + return $providers; | ||
| 24 | +} | ||
| 25 | + | ||
| 26 | +/** | ||
| 27 | + * Helper function for returning a themed image for the Kaixin display title. | ||
| 28 | + */ | ||
| 29 | +function csna_get_kaixin_button_image() { | ||
| 30 | + $image_arr = array( | ||
| 31 | + 'path' => drupal_get_path('module', 'csna_kaixin') . '/kaixin_135x24.png', | ||
| 32 | + 'title' => t('Sign in with Kaixin'), | ||
| 33 | + 'alt' => t('Sign in with Kaixin'), | ||
| 34 | + ); | ||
| 35 | + return theme('image', $image_arr); | ||
| 36 | +} | ||
| 37 | + | ||
| 38 | +/** | ||
| 39 | + * Implements hook_csna_provider_callback(). | ||
| 40 | + */ | ||
| 41 | +function csna_kaixin_csna_provider_callback($provider, $request) { | ||
| 42 | + if (isset($request['code'])) { | ||
| 43 | + $parameters = array( | ||
| 44 | + 'client_id' => $provider['key'], | ||
| 45 | + 'client_secret' => $provider['secret'], | ||
| 46 | + 'grant_type' => 'authorization_code', | ||
| 47 | + 'redirect_uri' => $provider['callback'], | ||
| 48 | + 'code' => $request['code'], | ||
| 49 | + ); | ||
| 50 | + $http = drupal_http_request(url($provider['access_token_uri'], array('query' => $parameters))); | ||
| 51 | + $data = json_decode($http->data); | ||
| 52 | + $http = drupal_http_request(url($provider['info_uri'], array('query' => array('access_token' => $data->access_token)))); | ||
| 53 | + $info = json_decode($http->data); | ||
| 54 | + if (!isset($info->uid)) { | ||
| 55 | + return FALSE; | ||
| 56 | + } | ||
| 57 | + return array( | ||
| 58 | + 'access_token' => $data->access_token, | ||
| 59 | + 'uid' => $info->uid, | ||
| 60 | + 'name' => $info->name, | ||
| 61 | + ); | ||
| 62 | + } | ||
| 63 | +} |
modules/csna/kaixin/kaixin_135x24.png
0 → 100644
1.84 KB
modules/csna/qq/csna_qq.info
0 → 100644
| 1 | +name = CSNA QQ | ||
| 2 | +description = Provide authentication integration for QQ. | ||
| 3 | +package = Authentication | ||
| 4 | +core = 7.x | ||
| 5 | +dependencies[] = csna | ||
| 6 | +configure = admin/config/services/csna | ||
| 7 | + | ||
| 8 | +; Information added by Drupal.org packaging script on 2015-10-19 | ||
| 9 | +version = "7.x-1.3" | ||
| 10 | +core = "7.x" | ||
| 11 | +project = "csna" | ||
| 12 | +datestamp = "1445231940" | ||
| 13 | + |
modules/csna/qq/csna_qq.install
0 → 100644
modules/csna/qq/csna_qq.module
0 → 100644
| 1 | +<?php | ||
| 2 | + | ||
| 3 | +/** | ||
| 4 | + * @file | ||
| 5 | + * The CSNA QQ module is a sub-module of the Chinese Social Networks | ||
| 6 | + * Authentication (CSNA) framework allowing integration with the QQ OAuth | ||
| 7 | + * protocol for Authentication/Login. | ||
| 8 | + */ | ||
| 9 | + | ||
| 10 | +/** | ||
| 11 | + * Implements hook_csna_provider_info(). | ||
| 12 | + */ | ||
| 13 | +function csna_qq_csna_provider_info() { | ||
| 14 | + $providers = array(); | ||
| 15 | + | ||
| 16 | + $providers['qq'] = array( | ||
| 17 | + 'title' => t('QQ'), | ||
| 18 | + 'description' => t('Set your <strong>QQ authorized KEY</strong> and <strong>SECRET</strong> below.<br/>If you want to use an API key, you can get one at the !keylink.', array('!keylink' => l(t('QQ API website'), 'http://connect.qq.com/', array('attributes' => array('target' => '_blank'))))), | ||
| 19 | + 'display_title' => csna_get_qq_button_image(), | ||
| 20 | + 'type' => CSNA_OAUTH2, | ||
| 21 | + 'authorize_uri' => 'https://graph.qq.com/oauth2.0/authorize', | ||
| 22 | + 'access_token_uri' => 'https://graph.qq.com/oauth2.0/token', | ||
| 23 | + 'info_uri' => 'https://graph.qq.com/user/get_user_info', | ||
| 24 | + ); | ||
| 25 | + | ||
| 26 | + return $providers; | ||
| 27 | +} | ||
| 28 | + | ||
| 29 | +/** | ||
| 30 | + * Helper function for returning a themed image for the QQ display title. | ||
| 31 | + */ | ||
| 32 | +function csna_get_qq_button_image() { | ||
| 33 | + $image_arr = array( | ||
| 34 | + 'path' => drupal_get_path('module', 'csna_qq') . '/qq_120x24.png', | ||
| 35 | + 'title' => t('Sign in with QQ'), | ||
| 36 | + 'alt' => t('Sign in with QQ'), | ||
| 37 | + ); | ||
| 38 | + return theme('image', $image_arr); | ||
| 39 | +} | ||
| 40 | + | ||
| 41 | +/** | ||
| 42 | + * Implements hook_csna_provider_callback(). | ||
| 43 | + */ | ||
| 44 | +function csna_qq_csna_provider_callback($provider, $request) { | ||
| 45 | + if (isset($request['code'])) { | ||
| 46 | + $parameters = array( | ||
| 47 | + 'client_id' => $provider['key'], | ||
| 48 | + 'client_secret' => $provider['secret'], | ||
| 49 | + 'grant_type' => 'authorization_code', | ||
| 50 | + 'redirect_uri' => $provider['callback'], | ||
| 51 | + 'code' => $request['code'], | ||
| 52 | + ); | ||
| 53 | + | ||
| 54 | + $param_data = array( | ||
| 55 | + 'method' => 'POST', | ||
| 56 | + 'data' => drupal_http_build_query($parameters), | ||
| 57 | + ); | ||
| 58 | + | ||
| 59 | + $http = drupal_http_request(url($provider['access_token_uri'], array('query' => $parameters)), $param_data); | ||
| 60 | + $data = explode('&', $http->data); | ||
| 61 | + $data = explode('=', reset($data)); | ||
| 62 | + $http = drupal_http_request('https://graph.qq.com/oauth2.0/me?' . $http->data); | ||
| 63 | + preg_match('/\{[^\}]*\}/', $http->data, $obj); | ||
| 64 | + $openid = json_decode($obj[0]); | ||
| 65 | + $http = drupal_http_request(url($provider['info_uri'], array( | ||
| 66 | + 'query' => array( | ||
| 67 | + 'access_token' => $data[1], | ||
| 68 | + 'oauth_consumer_key' => $provider['key'], | ||
| 69 | + 'openid' => $openid->openid,)))); | ||
| 70 | + $info = json_decode($http->data); | ||
| 71 | + return array( | ||
| 72 | + 'access_token' => $data[1], | ||
| 73 | + 'uid' => $openid->openid, | ||
| 74 | + 'name' => $info->nickname, | ||
| 75 | + 'avatar_link' => $info->figureurl_qq_2, | ||
| 76 | + ); | ||
| 77 | + } | ||
| 78 | +} |
modules/csna/qq/qq_120x24.png
0 → 100644
3.63 KB
modules/csna/renren/csna_renren.info
0 → 100644
| 1 | +name = CSNA Renren | ||
| 2 | +description = Provide authentication integration for Renren. | ||
| 3 | +package = Authentication | ||
| 4 | +core = 7.x | ||
| 5 | +dependencies[] = csna | ||
| 6 | +configure = admin/config/services/csna | ||
| 7 | + | ||
| 8 | +; Information added by Drupal.org packaging script on 2015-10-19 | ||
| 9 | +version = "7.x-1.3" | ||
| 10 | +core = "7.x" | ||
| 11 | +project = "csna" | ||
| 12 | +datestamp = "1445231940" | ||
| 13 | + |
modules/csna/renren/csna_renren.install
0 → 100644
modules/csna/renren/csna_renren.module
0 → 100644
| 1 | +<?php | ||
| 2 | + | ||
| 3 | +/** | ||
| 4 | + * @file | ||
| 5 | + * The CSNA Renren module is a sub-module of the Chinese Social Networks | ||
| 6 | + * Authentication (CSNA) framework allowing integration with the Renren OAuth | ||
| 7 | + * protocol for Authentication/Login. | ||
| 8 | + */ | ||
| 9 | + | ||
| 10 | +/** | ||
| 11 | + * Implements hook_csna_provider_info(). | ||
| 12 | + */ | ||
| 13 | +function csna_renren_csna_provider_info() { | ||
| 14 | + $providers = array(); | ||
| 15 | + | ||
| 16 | + $providers['renren'] = array( | ||
| 17 | + 'title' => t('Renren'), | ||
| 18 | + 'description' => t('Set your <strong>Renren authorized KEY</strong> and <strong>SECRET</strong> below.<br/>If you want to use an API key, you can get one at the !keylink.', array('!keylink' => l(t('Renren API website'), 'http://dev.renren.com/website', array('attributes' => array('target' => '_blank'))))), | ||
| 19 | + 'display_title' => csna_get_renren_button_image(), | ||
| 20 | + 'authorize_uri' => 'https://graph.renren.com/oauth/authorize', | ||
| 21 | + 'access_token_uri' => 'https://graph.renren.com/oauth/token', | ||
| 22 | + 'active' => TRUE, | ||
| 23 | + ); | ||
| 24 | + | ||
| 25 | + return $providers; | ||
| 26 | +} | ||
| 27 | + | ||
| 28 | +/** | ||
| 29 | + * Helper function for returning a themed image for the Renren display title. | ||
| 30 | + */ | ||
| 31 | +function csna_get_renren_button_image() { | ||
| 32 | + $image_arr = array( | ||
| 33 | + 'path' => drupal_get_path('module', 'csna_renren') . '/renren_133x28.png', | ||
| 34 | + 'title' => t('Sign in with Renren'), | ||
| 35 | + 'alt' => t('Sign in with Renren'), | ||
| 36 | + ); | ||
| 37 | + return theme('image', $image_arr); | ||
| 38 | +} | ||
| 39 | + | ||
| 40 | +/** | ||
| 41 | + * Implements hook_csna_provider_callback(). | ||
| 42 | + */ | ||
| 43 | +function csna_renren_csna_provider_callback($provider, $request) { | ||
| 44 | + if (isset($request['code'])) { | ||
| 45 | + $parameters = array( | ||
| 46 | + 'client_id' => $provider['key'], | ||
| 47 | + 'client_secret' => $provider['secret'], | ||
| 48 | + 'grant_type' => 'authorization_code', | ||
| 49 | + 'redirect_uri' => $provider['callback'], | ||
| 50 | + 'code' => $request['code'], | ||
| 51 | + ); | ||
| 52 | + | ||
| 53 | + $param_data = array( | ||
| 54 | + 'method' => 'POST', | ||
| 55 | + 'data' => drupal_http_build_query($parameters), | ||
| 56 | + ); | ||
| 57 | + | ||
| 58 | + $http = drupal_http_request(url($provider['access_token_uri'], array('query' => $parameters)), $param_data); | ||
| 59 | + $data = json_decode($http->data); | ||
| 60 | + if (!isset($data->user->id)) { | ||
| 61 | + return FALSE; | ||
| 62 | + } | ||
| 63 | + return array( | ||
| 64 | + 'access_token' => $data->access_token, | ||
| 65 | + 'uid' => $data->user->id, | ||
| 66 | + 'name' => $data->user->name, | ||
| 67 | + ); | ||
| 68 | + } | ||
| 69 | +} |
modules/csna/renren/renren_133x28.png
0 → 100644
2.8 KB
modules/csna/wechat/csna_wechat.info
0 → 100644
| 1 | +name = CSNA Wechat | ||
| 2 | +description = Provide authentication integration for Wechat. | ||
| 3 | +package = Authentication | ||
| 4 | +core = 7.x | ||
| 5 | +dependencies[] = csna | ||
| 6 | +configure = admin/config/services/csna | ||
| 7 | + | ||
| 8 | +; Information added by Drupal.org packaging script on 2015-10-19 | ||
| 9 | +version = "7.x-1.3" | ||
| 10 | +core = "7.x" | ||
| 11 | +project = "csna" | ||
| 12 | +datestamp = "1445231940" | ||
| 13 | + |
modules/csna/wechat/csna_wechat.install
0 → 100644
modules/csna/wechat/csna_wechat.module
0 → 100644
| 1 | +<?php | ||
| 2 | + | ||
| 3 | +/** | ||
| 4 | + * @file | ||
| 5 | + * The CSNA Wechat module is a sub-module of the Chinese Social Networks | ||
| 6 | + * Authentication (CSNA) framework allowing integration with the Wechat OAuth | ||
| 7 | + * protocol for Authentication/Login. | ||
| 8 | + */ | ||
| 9 | + | ||
| 10 | +/** | ||
| 11 | + * Implements hook_csna_provider_info(). | ||
| 12 | + */ | ||
| 13 | +function csna_wechat_csna_provider_info() { | ||
| 14 | + $providers = array(); | ||
| 15 | + | ||
| 16 | + $providers['wechat'] = array( | ||
| 17 | + 'title' => t('Wechat'), | ||
| 18 | + 'description' => t('Set your <strong>Wechat authorized KEY</strong> and <strong>SECRET</strong> below.<br/>If you want to use an API key, you can get one at the !keylink.', array('!keylink' => l(t('Wechat API website'), 'https://open.weixin.qq.com/', array('attributes' => array('target' => '_blank'))))), | ||
| 19 | + 'display_title' => csna_get_wechat_button_image(), | ||
| 20 | + 'type' => CSNA_OAUTH2, | ||
| 21 | + 'authorize_uri' => 'https://open.weixin.qq.com/connect/qrconnect', | ||
| 22 | + 'access_token_uri' => 'https://api.weixin.qq.com/sns/oauth2/access_token', | ||
| 23 | + 'info_uri' => 'https://api.weixin.qq.com/sns/userinfo', | ||
| 24 | + ); | ||
| 25 | + | ||
| 26 | + return $providers; | ||
| 27 | +} | ||
| 28 | + | ||
| 29 | +/** | ||
| 30 | + * Helper function for returning a themed image for the Wechat display title. | ||
| 31 | + */ | ||
| 32 | +function csna_get_wechat_button_image() { | ||
| 33 | + $image_arr = array( | ||
| 34 | + 'path' => drupal_get_path('module', 'csna_wechat') . '/wechat_120x24.png', | ||
| 35 | + 'title' => t('Sign in with Wechat'), | ||
| 36 | + 'alt' => t('Sign in with Wechat'), | ||
| 37 | + ); | ||
| 38 | + return theme('image', $image_arr); | ||
| 39 | +} | ||
| 40 | + | ||
| 41 | +/** | ||
| 42 | + * Implements hook_csna_provider_callback(). | ||
| 43 | + */ | ||
| 44 | +function csna_wechat_csna_provider_callback($provider, $request) { | ||
| 45 | + if (isset($request['code'])) { | ||
| 46 | + $parameters = array( | ||
| 47 | + 'appid' => $provider['key'], | ||
| 48 | + 'secret' => $provider['secret'], | ||
| 49 | + 'grant_type' => 'authorization_code', | ||
| 50 | + 'code' => $request['code'], | ||
| 51 | + ); | ||
| 52 | + | ||
| 53 | + $param_data = array( | ||
| 54 | + 'method' => 'POST', | ||
| 55 | + 'data' => drupal_http_build_query($parameters), | ||
| 56 | + ); | ||
| 57 | + | ||
| 58 | + $http = drupal_http_request(url($provider['access_token_uri'], array('query' => $parameters)), $param_data); | ||
| 59 | + $data = json_decode($http->data); | ||
| 60 | + $http = drupal_http_request(url($provider['info_uri'], array('query' => array('access_token' => $data->access_token, 'openid' => $data->openid)))); | ||
| 61 | + $info = json_decode($http->data); | ||
| 62 | + if (!isset($info->openid)) { | ||
| 63 | + return FALSE; | ||
| 64 | + } | ||
| 65 | + return array( | ||
| 66 | + 'access_token' => $data->access_token, | ||
| 67 | + 'uid' => $info->openid, | ||
| 68 | + 'name' => $info->nickname, | ||
| 69 | + ); | ||
| 70 | + } | ||
| 71 | +} |
modules/csna/wechat/wechat_120x24.png
0 → 100644
3.03 KB
modules/csna/weibo/csna_weibo.info
0 → 100644
| 1 | +name = CSNA Weibo | ||
| 2 | +description = Provide authentication integration for Weibo. | ||
| 3 | +package = Authentication | ||
| 4 | +core = 7.x | ||
| 5 | +dependencies[] = csna | ||
| 6 | +configure = admin/config/services/csna | ||
| 7 | + | ||
| 8 | +; Information added by Drupal.org packaging script on 2015-10-19 | ||
| 9 | +version = "7.x-1.3" | ||
| 10 | +core = "7.x" | ||
| 11 | +project = "csna" | ||
| 12 | +datestamp = "1445231940" | ||
| 13 | + |
modules/csna/weibo/csna_weibo.install
0 → 100644
modules/csna/weibo/csna_weibo.module
0 → 100644
| 1 | +<?php | ||
| 2 | +/** | ||
| 3 | + * @file | ||
| 4 | + * The CSNA Weibo module is a sub-module of the Chinese Social Networks | ||
| 5 | + * Authentication (CSNA) framework allowing integration with the Weibo OAuth | ||
| 6 | + * protocol for Authentication/Login. | ||
| 7 | + */ | ||
| 8 | + | ||
| 9 | +/** | ||
| 10 | + * Implements hook_csna_provider_info(). | ||
| 11 | + */ | ||
| 12 | +function csna_weibo_csna_provider_info() { | ||
| 13 | + $providers = array(); | ||
| 14 | + | ||
| 15 | + $providers['weibo'] = array( | ||
| 16 | + 'title' => t('Weibo Sina'), | ||
| 17 | + 'description' => t('Set your <strong>Sina Weibo authorized KEY</strong> and <strong>SECRET</strong> below.<br/>If you want to use an API key, you can get one at the !keylink.', array('!keylink' => l(t('Sina Weibo API website'), 'http://open.weibo.com/', array('attributes' => array('target' => '_blank'))))), | ||
| 18 | + 'display_title' => csna_get_weibo_button_image(), | ||
| 19 | + 'type' => CSNA_OAUTH2, | ||
| 20 | + 'authorize_uri' => 'https://api.weibo.com/oauth2/authorize', | ||
| 21 | + 'access_token_uri' => 'https://api.weibo.com/oauth2/access_token', | ||
| 22 | + 'info_uri' => 'https://api.weibo.com/2/users/show.json', | ||
| 23 | + ); | ||
| 24 | + | ||
| 25 | + return $providers; | ||
| 26 | +} | ||
| 27 | + | ||
| 28 | +/** | ||
| 29 | + * Helper function for returning a themed image for the Weibo display title. | ||
| 30 | + */ | ||
| 31 | +function csna_get_weibo_button_image() { | ||
| 32 | + $image_arr = array( | ||
| 33 | + 'path' => drupal_get_path('module', 'csna_weibo') . '/weibo_126x24.png', | ||
| 34 | + 'title' => t('Sign in with Weibo'), | ||
| 35 | + 'alt' => t('Sign in with Weibo'), | ||
| 36 | + ); | ||
| 37 | + return theme('image', $image_arr); | ||
| 38 | +} | ||
| 39 | + | ||
| 40 | +/** | ||
| 41 | + * Implements hook_csna_provider_callback(). | ||
| 42 | + */ | ||
| 43 | +function csna_weibo_csna_provider_callback($provider, $request) { | ||
| 44 | + if (isset($request['code'])) { | ||
| 45 | + $parameters = array( | ||
| 46 | + 'client_id' => $provider['key'], | ||
| 47 | + 'client_secret' => $provider['secret'], | ||
| 48 | + 'grant_type' => 'authorization_code', | ||
| 49 | + 'redirect_uri' => $provider['callback'], | ||
| 50 | + 'code' => $request['code'], | ||
| 51 | + ); | ||
| 52 | + | ||
| 53 | + $param_data = array( | ||
| 54 | + 'method' => 'POST', | ||
| 55 | + 'data' => drupal_http_build_query($parameters), | ||
| 56 | + ); | ||
| 57 | + | ||
| 58 | + $http = drupal_http_request(url($provider['access_token_uri'], array('query' => $parameters)), $param_data); | ||
| 59 | + $data = json_decode($http->data); | ||
| 60 | + $http = drupal_http_request(url($provider['info_uri'], array('query' => array('access_token' => $data->access_token, 'uid' => $data->uid)))); | ||
| 61 | + $info = json_decode($http->data); | ||
| 62 | + if (!isset($info->id)) { | ||
| 63 | + return FALSE; | ||
| 64 | + } | ||
| 65 | + return array( | ||
| 66 | + 'access_token' => $data->access_token, | ||
| 67 | + 'uid' => $info->id, | ||
| 68 | + 'name' => $info->name, | ||
| 69 | + 'avatar_link' => $info->avatar_large, | ||
| 70 | + ); | ||
| 71 | + } | ||
| 72 | +} |
modules/csna/weibo/weibo_126x24.png
0 → 100644
5.54 KB
modules/custom/csna_8/csna.api.php
0 → 100644
| 1 | +<?php | ||
| 2 | +/** | ||
| 3 | + * @file | ||
| 4 | + * API documentation for the Chinese Social Networks Authentication module. | ||
| 5 | + */ | ||
| 6 | + | ||
| 7 | +use Drupal\core\Url; | ||
| 8 | +use GuzzleHttp\Exception\RequestException; | ||
| 9 | + | ||
| 10 | +/** | ||
| 11 | + * Define Authentication providers available to the CSNA framework. | ||
| 12 | + * | ||
| 13 | + * The Chinese Social Networks Authentication (CSNA) module uses this hook to | ||
| 14 | + * gather information on provider authentication methods defined by enabled | ||
| 15 | + * modules. These methods depend on a variety of properties used by CSNA to | ||
| 16 | + * integrate with third party API providers based on the OAuth protocol. | ||
| 17 | + * | ||
| 18 | + * By default CSNA supports the following Authentication API providers through | ||
| 19 | + * sub-modules: | ||
| 20 | + * - Sina weibo (新浪微博), Chinese twitter like website. | ||
| 21 | + * - Tencent (QQ), biggest Chinese IM provider. | ||
| 22 | + * - Renren(人人网), biggest Chinese facebook like website. | ||
| 23 | + * - Kaixin001(开心网), secondary Chinese facebook like website. | ||
| 24 | + * | ||
| 25 | + * This hook allows other modules to define custom authentication third party | ||
| 26 | + * API providers by defining all the necessary information for CSNA's | ||
| 27 | + * implementation of the OAuth protocol. | ||
| 28 | + * | ||
| 29 | + * @return array | ||
| 30 | + * An array of providers keyed by provider_id with the following properties: | ||
| 31 | + * - title: The title or name of the defined provider. | ||
| 32 | + * - description: Description text to appear on the admin page for the | ||
| 33 | + * configuration of the required parameters for this specific provider, | ||
| 34 | + * such as Authentication API KEY or Password. | ||
| 35 | + * - display_title: The title to be displayed in the list of links of | ||
| 36 | + * providers returned by theme_csna_providers, which displays in the user | ||
| 37 | + * login/registration forms and block. For better usage, HTML is allowed | ||
| 38 | + * for this property, for example to display an image or logo. | ||
| 39 | + * - type: string identifying the type of OAuth protocol used. By default, | ||
| 40 | + * CSNA provides a constant for 'oauth2', see CSNA_OAUTH2, but any other | ||
| 41 | + * custom OAuth type could also be used and provided for this property. | ||
| 42 | + * - authorize_uri: The URL used by providers to authenticate users through | ||
| 43 | + * the OAuth protocol. | ||
| 44 | + * - access_token_uri: The URL used by CSNA to get the authentication token | ||
| 45 | + * returned by providers if operation was successful. | ||
| 46 | + * - info_uri: This URL allows capturing User's information from third party | ||
| 47 | + * authentication providers, such as username, or other useful information. | ||
| 48 | + * | ||
| 49 | + * @see csna_providers() | ||
| 50 | + * @see csna_weibo_csna_provider_info() | ||
| 51 | + */ | ||
| 52 | +function hook_csna_provider_info() { | ||
| 53 | + // Example taken from the csna_weibo sub-module. | ||
| 54 | + $providers = array(); | ||
| 55 | + | ||
| 56 | + $providers['weibo'] = array( | ||
| 57 | + 'title' => t('Weibo Sina'), | ||
| 58 | + 'description' => t('Set your Sina Weibo authorized KEY and SECRET below.'), | ||
| 59 | + 'display_title' => csna_get_weibo_button_image(), | ||
| 60 | + 'type' => CSNA_OAUTH2, | ||
| 61 | + 'authorize_uri' => 'https://api.weibo.com/oauth2/authorize', | ||
| 62 | + 'access_token_uri' => 'https://api.weibo.com/oauth2/access_token', | ||
| 63 | + 'info_uri' => 'https://api.weibo.com/2/users/show.json', | ||
| 64 | + ); | ||
| 65 | + | ||
| 66 | + return $providers; | ||
| 67 | +} | ||
| 68 | + | ||
| 69 | +/** | ||
| 70 | + * Allows other modules to alter already defined list of providers. | ||
| 71 | + * | ||
| 72 | + * Any of the providers and any of their properties or values can be modified | ||
| 73 | + * by using an implementation of this hook. | ||
| 74 | + * | ||
| 75 | + * @param array $providers | ||
| 76 | + * An associative array of providers keyed by the provider_id, as returned by | ||
| 77 | + * the function csna_providers(). See hook_csna_provider_info for a detailed | ||
| 78 | + * list of all the defined and required properties for each provider. | ||
| 79 | + * | ||
| 80 | + * @see hook_csna_provider_info() | ||
| 81 | + * @see csna_providers() | ||
| 82 | + */ | ||
| 83 | +/*function hook_csna_provider_info_alter(&$providers) { | ||
| 84 | + if (isset($providers['weibo'])) { | ||
| 85 | + $providers['weibo']['display_title'] = t("Login or register with your Sina Weibo account!"); | ||
| 86 | + } | ||
| 87 | +} | ||
| 88 | +*/ | ||
| 89 | +/** | ||
| 90 | + * Define providers custom authentication callback methods. | ||
| 91 | + * | ||
| 92 | + * The implementation of this hook is usually required when defining a Third | ||
| 93 | + * Party authentication OAuth API provider through hook_csna_provider_info. | ||
| 94 | + * | ||
| 95 | + * This hook callback is executed when returning from provider's API | ||
| 96 | + * authentication pages, with information about the operation, such as whether | ||
| 97 | + * it was successful or not. In case of success, most providers will return a | ||
| 98 | + * token or code that can be further used to verify or obtain user's | ||
| 99 | + * information through the $provider['info_uri'] defined URL. | ||
| 100 | + * | ||
| 101 | + * @param array $provider | ||
| 102 | + * An array of properties for the corresponding provider defined through | ||
| 103 | + * hook_csna_provider_info, see API hooks documentation for more information. | ||
| 104 | + * @param array $request | ||
| 105 | + * A PHP predefined variable for HTTP Request variables: $_REQUEST, received | ||
| 106 | + * from the third party authentication provider. | ||
| 107 | + * | ||
| 108 | + * @return array | ||
| 109 | + * An array of properties including the following keys and values: | ||
| 110 | + * - access_token: The access token returned by the provider through its | ||
| 111 | + * access_token_uri URL to provider further access to user's information if | ||
| 112 | + * authentication was successful. | ||
| 113 | + * - uid: The ID of the user returned from the provider used to load user | ||
| 114 | + * account through user_external_load (see core API). | ||
| 115 | + * - name: The user name returned from the provider used to load user account | ||
| 116 | + * account through user_load_by_name (see core API). | ||
| 117 | + * | ||
| 118 | + * @see csna_callback() | ||
| 119 | + * @see csna_kaixin_csna_provider_callback() | ||
| 120 | + */ | ||
| 121 | +function hook_csna_provider_callback($provider, $request) { | ||
| 122 | + // Example taken from the csna_kaixin sub-module. | ||
| 123 | + if (isset($request['code'])) { | ||
| 124 | + $parameters = array( | ||
| 125 | + 'client_id' => $provider['key'], | ||
| 126 | + 'client_secret' => $provider['secret'], | ||
| 127 | + 'grant_type' => 'authorization_code', | ||
| 128 | + 'redirect_uri' => $provider['callback'], | ||
| 129 | + 'code' => $request['code'], | ||
| 130 | + ); | ||
| 131 | + $client = \Drupal::httpClient(); | ||
| 132 | + $request = $client->request('GET', Url::fromUri($provider['access_token_uri'], array('query' => $parameters))); | ||
| 133 | + $response_data = ''; | ||
| 134 | + try { | ||
| 135 | + $response = $client->send($request); | ||
| 136 | + // Expected result. | ||
| 137 | + $response_data = $response->getBody(); | ||
| 138 | + } | ||
| 139 | + catch (RequestException $e) { | ||
| 140 | + } | ||
| 141 | + $data = json_decode($response_data); | ||
| 142 | + $request = $client->request('GET', Url::fromUri($provider['info_uri'], array('query' => array('access_token' => $data->access_token)))); | ||
| 143 | + try { | ||
| 144 | + $response = $client->send($request); | ||
| 145 | + // Expected result. | ||
| 146 | + $response_data = $response->getBody(); | ||
| 147 | + } | ||
| 148 | + catch (RequestException $e) { | ||
| 149 | + } | ||
| 150 | + $info = json_decode($response_data); | ||
| 151 | + if (!isset($info->uid)) { | ||
| 152 | + return FALSE; | ||
| 153 | + } | ||
| 154 | + return array( | ||
| 155 | + 'access_token' => $data->access_token, | ||
| 156 | + 'uid' => $info->uid, | ||
| 157 | + 'name' => $info->name, | ||
| 158 | + ); | ||
| 159 | + } | ||
| 160 | + return FALSE; | ||
| 161 | +} |
modules/custom/csna_8/csna.info.yml
0 → 100644
modules/custom/csna_8/csna.links.menu.yml
0 → 100644
| 1 | +csna.admin: | ||
| 2 | + title: 'Chinese Social Networks Authentication settings (CSNA)' | ||
| 3 | + description: 'Configure the CSNA key or secrect code settings for third party authentication API providers.' | ||
| 4 | + parent: system.admin_config_development | ||
| 5 | + route_name: csna.config | ||
| 6 | + weight: 100 | ||
| 7 | +csna.callback: | ||
| 8 | + title: 'Authentication callback' | ||
| 9 | + route_name: csna.callback |
modules/custom/csna_8/csna.module
0 → 100644
| 1 | +<?php | ||
| 2 | + | ||
| 3 | +use Drupal\Core\Url; | ||
| 4 | +use Drupal\Core\Form\FormStateInterface; | ||
| 5 | + | ||
| 6 | +/** | ||
| 7 | + * Returns an array of OAuth Third Party authentication providers. | ||
| 8 | + * | ||
| 9 | + * CSNA's API Framework provides a method for any enabled module to define | ||
| 10 | + * additional authentication providers. This function gathers information on | ||
| 11 | + * provider authentication methods defined by enabled modules. | ||
| 12 | + * | ||
| 13 | + * @param bool $valid | ||
| 14 | + * @return array An associative array of providers keyed by the provider_id. | ||
| 15 | + * An associative array of providers keyed by the provider_id. | ||
| 16 | + * @see hook_csna_provider_info() | ||
| 17 | + */ | ||
| 18 | +function csna_providers($valid = FALSE) { | ||
| 19 | + static $providers; | ||
| 20 | + | ||
| 21 | + if (!isset($providers)) { | ||
| 22 | + $providers = array(); | ||
| 23 | + | ||
| 24 | + // Build the providers array, including module names for the purpose | ||
| 25 | + // of including files if necessary. | ||
| 26 | + // An associative array of providers objects keyed by the provider_id. | ||
| 27 | + $module_handler = \Drupal::moduleHandler(); | ||
| 28 | + | ||
| 29 | + foreach ($module_handler->getImplementations('csna_provider_info') as $module) { | ||
| 30 | + foreach ($module_handler->invoke($module, 'csna_provider_info') as $provider_id => $provider) { | ||
| 31 | + $config = \Drupal::config('csna.' . $provider); | ||
| 32 | + $provider['provider_id'] = $provider_id; | ||
| 33 | + $provider['module'] = $module; | ||
| 34 | + $provider['key'] = $config->get('csna_' . $provider_id . '_key'); | ||
| 35 | + $provider['secret'] = $config->get('csna_' . $provider_id . '_secret'); | ||
| 36 | + $providers[$provider_id] = $provider; | ||
| 37 | + if ($valid && (empty($provider['key']) || empty($provider['secret']))) { | ||
| 38 | + unset($providers[$provider_id]); | ||
| 39 | + } | ||
| 40 | + } | ||
| 41 | + } | ||
| 42 | + | ||
| 43 | + $module_handler->alter('csna_provider_info', $providers); | ||
| 44 | + | ||
| 45 | + foreach ($providers as $provider_id => & $provider) { | ||
| 46 | + $defaults = array( | ||
| 47 | + 'provider_id' => $provider_id, | ||
| 48 | + 'base' => $provider_id, | ||
| 49 | + 'title' => '', | ||
| 50 | + 'description' => '', | ||
| 51 | + 'active' => FALSE, | ||
| 52 | + 'callback' => Url::fromRoute('csna.callback',array('csna_provider' => $provider_id), array('absolute' => TRUE)), | ||
| 53 | + 'file' => '', | ||
| 54 | + ); | ||
| 55 | + | ||
| 56 | + $provider += $defaults; | ||
| 57 | + | ||
| 58 | + // Default the display title to the title if necessary. The display | ||
| 59 | + // title is used in instances where the login method has an official | ||
| 60 | + // name but a different method of display on selection forms (like some | ||
| 61 | + // text and a set of images). | ||
| 62 | + if (empty($provider['display_title'])) { | ||
| 63 | + $provider['display_title'] = $provider['title']; | ||
| 64 | + } | ||
| 65 | + | ||
| 66 | + // Default the short title to the title if necessary. Like the display | ||
| 67 | + // title, the short title is an alternate way of displaying the title to | ||
| 68 | + // the user consisting of plain text but with unnecessary information | ||
| 69 | + // stripped off. | ||
| 70 | + if (empty($provider[$provider_id]['short_title'])) { | ||
| 71 | + $provider['short_title'] = $provider['title']; | ||
| 72 | + } | ||
| 73 | + } | ||
| 74 | + } | ||
| 75 | + | ||
| 76 | + return $providers; | ||
| 77 | +} | ||
| 78 | + | ||
| 79 | + | ||
| 80 | +function csna_form_alter(&$form, \Drupal\Core\Form\FormStateInterface $form_state, $form_id) { | ||
| 81 | + //$form_id == 'user_login' || $form_id == 'user_login_block' || $form_id == 'user_register_form' | ||
| 82 | + if ( $form_id == 'user_login_form' ) { | ||
| 83 | + $providers = csna_providers(); | ||
| 84 | + | ||
| 85 | + // if admin form | ||
| 86 | + if (empty($form['administer_users']['#value'])) { | ||
| 87 | + $csna_provider = array( | ||
| 88 | + '#theme' => 'csna_providers', | ||
| 89 | + '#attributes' => array('providers' => $providers), | ||
| 90 | + ); | ||
| 91 | + | ||
| 92 | + if (isset($form['submitted']['user_login_block']['#suffix']) && !empty($form['submitted']['user_login_block']['#suffix'])) { | ||
| 93 | + $form['submitted']['user_login_block']['#suffix'] .= drupal_render($csna_provider); | ||
| 94 | + } | ||
| 95 | + else { | ||
| 96 | + $form['submitted']['user_login_block']['#suffix'] = drupal_render($csna_provider); | ||
| 97 | + } | ||
| 98 | + } | ||
| 99 | + } | ||
| 100 | + dpm($form_id); | ||
| 101 | + // dpm($form); | ||
| 102 | +} | ||
| 103 | +/** | ||
| 104 | + * Implements hook_theme(). | ||
| 105 | + */ | ||
| 106 | +function csna_theme($existing, $type, $theme, $path) { | ||
| 107 | + $providers = csna_providers(); | ||
| 108 | + return array( | ||
| 109 | + 'csna_providers' => array( | ||
| 110 | + 'variables' => array('providers' => $providers), | ||
| 111 | + ), | ||
| 112 | + ); | ||
| 113 | +} | ||
| 114 | + | ||
| 115 | + | ||
| 116 | + | ||
| 117 | +/** | ||
| 118 | + * Render a themed list of links to providers authorized login URL pages. | ||
| 119 | + * | ||
| 120 | + * @param array $providers | ||
| 121 | + * An associative array of providers keyed by the provider_id, as returned by | ||
| 122 | + * the function csna_providers(). | ||
| 123 | + * Mostly the display_title property of providers is used in this function | ||
| 124 | + * to display a custom title, name or even HTML to be linked to corresponding | ||
| 125 | + * provider's authorized login URL page. See API documentation for more | ||
| 126 | + * information on providers available properties. | ||
| 127 | + * | ||
| 128 | + * @see csna_providers() | ||
| 129 | + * @see hook_csna_provider_info() | ||
| 130 | + */ | ||
| 131 | +function template_preprocess_csna_providers(&$vars) { | ||
| 132 | + dpm($vars); | ||
| 133 | + $providers = $vars['providers']; | ||
| 134 | + $items = array(); | ||
| 135 | + foreach ($providers as $provider_id => $provider) { | ||
| 136 | + $items[] = array( | ||
| 137 | + 'data' => \Drupal::l($provider['display_title'], Url::fromRoute('csna.redirect', array('csna_provider' => $provider_id), array('html' => TRUE))), | ||
| 138 | + 'id' => 'csna_provider_' . $provider_id, | ||
| 139 | + ); | ||
| 140 | + } | ||
| 141 | + | ||
| 142 | + $item_list = array( | ||
| 143 | + '#type' => 'item_list', | ||
| 144 | + 'items' => $items, | ||
| 145 | + 'attributes' => array('class' => 'csna-items'), | ||
| 146 | + ); | ||
| 147 | + return drupal_render($item_list); | ||
| 148 | +} |
modules/custom/csna_8/csna.routing.yml
0 → 100644
| 1 | +csna.config: | ||
| 2 | + path: '/admin/config/services/csna' | ||
| 3 | + defaults: | ||
| 4 | + _title: 'Chinese Social Networks Authentication settings (CSNA)' | ||
| 5 | + _form: '\Drupal\csna\Form\SettingsForm' | ||
| 6 | + options: | ||
| 7 | + _admin_route: TRUE | ||
| 8 | + requirements: | ||
| 9 | + _permission: 'administer site configuration' | ||
| 10 | +csna.redirect: | ||
| 11 | + path: 'csna/{csna_provider}' | ||
| 12 | + defaults: | ||
| 13 | + _controller: '\Drupal\csna\Controller\CsnaController::csna_redirect' | ||
| 14 | + _title: 'Authentication redirect' | ||
| 15 | + | ||
| 16 | +csna.callback: | ||
| 17 | + path: '/csna/{csna_provider}/callback' | ||
| 18 | + defaults: | ||
| 19 | + _controller: '\Drupal\csna\Controller\CsnaController::csna_callback' | ||
| 20 | + _title: 'Authentication callback' | ||
| 21 | + requirements: | ||
| 22 | + _access: 'user_is_anonymous' |
modules/custom/csna_8/qq/csna_qq.info.yml
0 → 100644
modules/custom/csna_8/qq/csna_qq.module
0 → 100644
| 1 | +<?php | ||
| 2 | + | ||
| 3 | +use Drupal\Core\Url; | ||
| 4 | + | ||
| 5 | +/** | ||
| 6 | + * @file | ||
| 7 | + * The CSNA QQ module is a sub-module of the Chinese Social Networks | ||
| 8 | + * Authentication (CSNA) framework allowing integration with the QQ OAuth | ||
| 9 | + * protocol for Authentication/Login. | ||
| 10 | + */ | ||
| 11 | + | ||
| 12 | +/** | ||
| 13 | + * Implements hook_csna_provider_info(). | ||
| 14 | + */ | ||
| 15 | +function csna_qq_csna_provider_info() { | ||
| 16 | + $providers = array(); | ||
| 17 | + | ||
| 18 | + $providers['qq'] = array( | ||
| 19 | + 'title' => t('QQ'), | ||
| 20 | + 'description' => t('Set your <strong>QQ authorized KEY</strong> and <strong>SECRET</strong> below.<br/>If you want to use an API key, you can get one at the !keylink.', array('!keylink' => \Drupal::l(t('QQ API website'), Url::fromUri('http://connect.qq.com/', array('attributes' => array('target' => '_blank')))))), | ||
| 21 | + 'display_title' => csna_get_qq_button_image(), | ||
| 22 | + 'type' => CSNA_OAUTH2, | ||
| 23 | + 'authorize_uri' => 'https://graph.qq.com/oauth2.0/authorize', | ||
| 24 | + 'access_token_uri' => 'https://graph.qq.com/oauth2.0/token', | ||
| 25 | + 'info_uri' => 'https://graph.qq.com/user/get_user_info', | ||
| 26 | + ); | ||
| 27 | + | ||
| 28 | + return $providers; | ||
| 29 | +} | ||
| 30 | + | ||
| 31 | +/** | ||
| 32 | + * Helper function for returning a themed image for the QQ display title. | ||
| 33 | + */ | ||
| 34 | +function csna_get_qq_button_image() { | ||
| 35 | + $image_arr = array( | ||
| 36 | + 'path' => drupal_get_path('module', 'csna_qq') . '/qq_120x24.png', | ||
| 37 | + 'title' => t('Sign in with QQ'), | ||
| 38 | + 'alt' => t('Sign in with QQ'), | ||
| 39 | + ); | ||
| 40 | + //return theme('image', $image_arr); | ||
| 41 | + return ''; | ||
| 42 | +} |
| 1 | +<?php | ||
| 2 | +/** | ||
| 3 | + * @file | ||
| 4 | + *Contains \Drupal\csna\Controller\CsnaController. | ||
| 5 | + */ | ||
| 6 | + | ||
| 7 | +namespace Drupal\csna\Controller; | ||
| 8 | + | ||
| 9 | +use Drupal\Core\Controller\ControllerBase; | ||
| 10 | +use Symfony\Component\HttpFoundation\RedirectResponse; | ||
| 11 | + | ||
| 12 | +class CsnaController extends ControllerBase | ||
| 13 | +{ | ||
| 14 | + | ||
| 15 | + /** | ||
| 16 | + * Menu callback: CSNA Redirect. | ||
| 17 | + */ | ||
| 18 | + function csna_redirect( $provider ) | ||
| 19 | + { | ||
| 20 | + $parameters = array( | ||
| 21 | + 'client_id' => $provider['key'], | ||
| 22 | + 'redirect_uri' => $provider['callback'], | ||
| 23 | + 'response_type' => 'code', | ||
| 24 | + ); | ||
| 25 | + if ($provider['provider_id'] == 'wechat') { | ||
| 26 | + unset($parameters['client_id']); | ||
| 27 | + $parameters['appid'] = $provider['key']; | ||
| 28 | + $parameters['scope'] = 'snsapi_login'; | ||
| 29 | + } | ||
| 30 | + return new RedirectResponse(\Drupal::url($provider['authorize_uri'], array('query' => $parameters))); | ||
| 31 | + } | ||
| 32 | + | ||
| 33 | + /** | ||
| 34 | + * @param $provider | ||
| 35 | + */ | ||
| 36 | + public function csna_callback( $provider ) | ||
| 37 | + { | ||
| 38 | + global $user; | ||
| 39 | + $module_handler = \Drupal::moduleHandler(); | ||
| 40 | + $data = $module_handler->invoke($provider['module'], 'csna_provider_callback', array($provider, $_REQUEST)); | ||
| 41 | + | ||
| 42 | + // Forcing array format because of Sina weibo will return an Object. | ||
| 43 | + if (!is_array($data)) { | ||
| 44 | + $data = (array) $data; | ||
| 45 | + } | ||
| 46 | + | ||
| 47 | + if (isset($data['access_token'])) { | ||
| 48 | + $identity = $provider['provider_id'] . '_' . $data['uid']; | ||
| 49 | + $account = user_external_load($identity); | ||
| 50 | + | ||
| 51 | + if (!isset($account->uid)) { | ||
| 52 | + $name = $data['name']; | ||
| 53 | + $ac = user_load_by_name($name); | ||
| 54 | + if ($ac) { | ||
| 55 | + $separator = '_'; | ||
| 56 | + $i = 0; | ||
| 57 | + do { | ||
| 58 | + $i++; | ||
| 59 | + $name = $data['name'] . $separator . $i; | ||
| 60 | + } while (user_load_by_name($name)); | ||
| 61 | + } | ||
| 62 | + //User avatar | ||
| 63 | + if (isset($data['avatar_link'])) { | ||
| 64 | + $avatar_directory = file_default_scheme() . '://' . variable_get('user_picture_path', 'pictures'); | ||
| 65 | + $avatar = system_retrieve_file($data['avatar_link'], $avatar_directory, TRUE, FILE_EXISTS_RENAME); | ||
| 66 | + } | ||
| 67 | + $edit = array( | ||
| 68 | + 'name' => $name, | ||
| 69 | + 'status' => 1, | ||
| 70 | + 'picture' => isset($avatar->fid) ? $avatar->fid : '', | ||
| 71 | + ); | ||
| 72 | + $account = user_save(NULL, $edit); | ||
| 73 | + user_set_authmaps($account, array('authname_csna' => $identity)); | ||
| 74 | + } | ||
| 75 | + | ||
| 76 | + csna_execute_user_login($account); | ||
| 77 | + | ||
| 78 | + if (variable_get('csna_require_email', TRUE) && empty($account->mail)) { | ||
| 79 | + drupal_goto('csna/' . $account->uid . '/complete-register'); | ||
| 80 | + } | ||
| 81 | + } | ||
| 82 | + drupal_goto('user'); | ||
| 83 | + } | ||
| 84 | +} | ||
| 85 | + |
| 1 | +<?php | ||
| 2 | + | ||
| 3 | +/** | ||
| 4 | + * @file | ||
| 5 | + * Contains \Drupal\csna\Form\SettingsForm. | ||
| 6 | + */ | ||
| 7 | + | ||
| 8 | +namespace Drupal\csna\Form; | ||
| 9 | + | ||
| 10 | +use Drupal\Core\Form\ConfigFormBase; | ||
| 11 | +use Symfony\Component\HttpFoundation\Request; | ||
| 12 | +use Drupal\Core\Form\FormStateInterface; | ||
| 13 | +use Drupal\Core\Url; | ||
| 14 | + | ||
| 15 | +/** | ||
| 16 | + * Defines a form that configures csna settings. | ||
| 17 | + */ | ||
| 18 | +class SettingsForm extends ConfigFormBase { | ||
| 19 | + /** | ||
| 20 | + * {@inheritdoc} | ||
| 21 | + */ | ||
| 22 | + public function getFormId() { | ||
| 23 | + return 'csna_admin_settings_form'; | ||
| 24 | + } | ||
| 25 | + | ||
| 26 | + /** | ||
| 27 | + * {@inheritdoc} | ||
| 28 | + */ | ||
| 29 | + protected function getEditableConfigNames() { | ||
| 30 | + return [ | ||
| 31 | + 'csna.settings', | ||
| 32 | + ]; | ||
| 33 | + } | ||
| 34 | + | ||
| 35 | + /** | ||
| 36 | + * {@inheritdoc} | ||
| 37 | + */ | ||
| 38 | + public function buildForm(array $form, FormStateInterface $form_state, Request $request = NULL) { | ||
| 39 | + $providers = csna_providers(); | ||
| 40 | + foreach ($providers as $provider_id => $provider) { | ||
| 41 | + $config = \Drupal::config('csna.' . $provider); | ||
| 42 | + $form[$provider_id] = array( | ||
| 43 | + '#type' => 'fieldset', | ||
| 44 | + '#title' => $provider['title'], | ||
| 45 | + '#description' => $provider['description'], | ||
| 46 | + ); | ||
| 47 | + $form[$provider_id]['csna_' . $provider_id . '_key'] = array( | ||
| 48 | + '#type' => 'textfield', | ||
| 49 | + '#title' => t('Key'), | ||
| 50 | + '#size' => 40, | ||
| 51 | + '#maxlength' => 255, | ||
| 52 | + '#default_value' => $config->get('csna_' . $provider_id . '_key'), | ||
| 53 | + ); | ||
| 54 | + $form[$provider_id]['csna_' . $provider_id . '_secret'] = array( | ||
| 55 | + '#type' => 'textfield', | ||
| 56 | + '#title' => t('Secret'), | ||
| 57 | + '#size' => 40, | ||
| 58 | + '#maxlength' => 255, | ||
| 59 | + '#default_value' => $config->get('csna_' . $provider_id . '_secret'), | ||
| 60 | + ); | ||
| 61 | + } | ||
| 62 | + | ||
| 63 | + // If no provider/sub-module was found, provide a default help text. | ||
| 64 | + if (!isset($form)) { | ||
| 65 | + $form['default_message'] = array( | ||
| 66 | + '#markup' => t('<strong>No CSNA third party API provider module has been enabled yet</strong>.<br/>Please enable <strong>at least a CSNA sub-module</strong> or any other <strong>CSNA API provider</strong> from the !modadminlink then feel free to browse this page again.<br/>See more information on !projectlink about <strong>supported providers</strong> and <strong>installation instructions</strong>.', array( | ||
| 67 | + '!modadminlink' => \Drupal::l(t('module administration page'), Url::fromRoute('system.modules_list')), | ||
| 68 | + '!projectlink' => \Drupal::l(t("module project's page"), Url::fromUri('http://drupal.org/project/csna', array('attributes' => array('target' => '_blank')))), | ||
| 69 | + )), | ||
| 70 | + ); | ||
| 71 | + return parent::buildForm($form, $form_state); | ||
| 72 | + } | ||
| 73 | + else { | ||
| 74 | + $config = \Drupal::config('csna.settings'); | ||
| 75 | + $form['csna_require_email'] = array( | ||
| 76 | + '#type' => 'checkbox', | ||
| 77 | + '#title' => t('Require email'), | ||
| 78 | + '#description' => t('Require user entering email after successful user login if email hasn\'t been set yet.'), | ||
| 79 | + '#default_value' => $config->get('csna_require_email'), | ||
| 80 | + ); | ||
| 81 | + | ||
| 82 | + return parent::buildForm($form, $form_state); | ||
| 83 | + } | ||
| 84 | + } | ||
| 85 | + | ||
| 86 | + | ||
| 87 | + /** | ||
| 88 | + * {@inheritdoc} | ||
| 89 | + */ | ||
| 90 | + public function submitForm(array &$form, FormStateInterface $form_state) { | ||
| 91 | + parent::submitForm($form, $form_state); | ||
| 92 | + $providers = csna_providers(); | ||
| 93 | + foreach ($providers as $provider_id => $provider) { | ||
| 94 | + $config_providers = \Drupal::service('config.factory')->getEditable('csna.' . $provider); | ||
| 95 | + // Let active plugins save their settings. | ||
| 96 | + $config_providers->set('csna_' . $provider_id . '_key', $form_state->getValue('csna_' . $provider_id . '_key')); | ||
| 97 | + $config_providers->set('csna_' . $provider_id . '_secret', $form_state->getValue('csna_' . $provider_id . '_secret')); | ||
| 98 | + $config_providers->save(); | ||
| 99 | + } | ||
| 100 | + $config_settings = \Drupal::service('config.factory')->getEditable('csna.settings'); | ||
| 101 | + $config_settings->set('csna_require_email', $form_state->getValue('csna_require_email')); | ||
| 102 | + $config_settings->save(); | ||
| 103 | + } | ||
| 104 | +} |
Please
register
or
login
to post a comment