Project Development

Version 170 (Quentin Durand, 10/19/2017 03:43 pm)

1 1 Etienne Pallier
h1. Project Development
2 2 Etienne Pallier
3 1 Etienne Pallier
4 143 Etienne Pallier
This page describes the development process, and some useful tools.
5 2 Etienne Pallier
6 2 Etienne Pallier
7 145 Etienne Pallier
{{>toc}}
8 145 Etienne Pallier
9 145 Etienne Pallier
10 145 Etienne Pallier
---
11 145 Etienne Pallier
12 145 Etienne Pallier
h2. %{margin-left:0px; font-weight:bold; font-size:25px;  display:block; color:red;}USEFUL LINKS%
13 145 Etienne Pallier
14 145 Etienne Pallier
15 166 Etienne Pallier
* Simulateur de Telescope (malheureusement Win only je crois): http://www.ascom-standards.org
16 1 Etienne Pallier
17 166 Etienne Pallier
* Django.test Client : https://docs.djangoproject.com/fr/1.10/topics/testing/tools
18 166 Etienne Pallier
19 166 Etienne Pallier
* Pyros Demo online (intranet) : http://hyperion2.irap.omp.eu:8000/routine_manager
20 158 Etienne Pallier
21 143 Etienne Pallier
* I-notify: http://linuxfr.org/news/exploiter-inotify-c-est-simple
22 84 Paul Carensac
23 143 Etienne Pallier
* Project Installation page : [[Project Installation]]
24 1 Etienne Pallier
25 143 Etienne Pallier
* HOWTO Format Redmine Wiki : http://www.redmine.org/projects/redmine/wiki/FrRedmineWikiFormatting
26 1 Etienne Pallier
27 143 Etienne Pallier
* Project's applications : [[Pyros applications]]
28 103 Etienne Pallier
29 143 Etienne Pallier
* Technical components : [[Technical components]]
30 1 Etienne Pallier
31 102 Etienne Pallier
* History of commits : https://gitlab.irap.omp.eu/epallier/pyros/commits/master
32 143 Etienne Pallier
33 130 Etienne Pallier
* OLD pyros version doc (Alexandru) : https://projects.irap.omp.eu/projects/gft/wiki/Documentation_technique_projet
34 130 Etienne Pallier
35 143 Etienne Pallier
36 143 Etienne Pallier
37 143 Etienne Pallier
38 2 Etienne Pallier
39 2 Etienne Pallier
40 2 Etienne Pallier
---
41 3 Etienne Pallier
42 167 Etienne Pallier
h2. %{margin-left:0px; font-weight:bold; font-size:25px;  display:block; color:red;}CONVENTIONS DE CODAGE%
43 167 Etienne Pallier
44 167 Etienne Pallier
http://planetowiki.irap.omp.eu/do/view/Main/HowtoInformatique#Conventions_de_Codage_en_Python
45 167 Etienne Pallier
46 167 Etienne Pallier
47 167 Etienne Pallier
48 167 Etienne Pallier
---
49 167 Etienne Pallier
50 112 Etienne Pallier
h2. %{margin-left:0px; font-weight:bold; font-size:25px;  display:block; color:red;}TODO LIST%
51 112 Etienne Pallier
52 165 Etienne Pallier
Aller sur la page [[TODO]]
53 117 Etienne Pallier
54 125 Etienne Pallier
h2. %{margin-left:0px; font-weight:bold; font-size:25px;  display:block; color:red;}PLAN OF WORK (ROADMAP)%
55 122 Etienne Pallier
56 1 Etienne Pallier
57 133 Etienne Pallier
Le stage se déroule du 14 mars au 12 aout, soit environ 5 mois, soit exactement 22 semaines (S1 à S22), ou 44 demi-semaines.
58 132 Etienne Pallier
_*(Ne pas oublier de rédiger le rapport de stage au fur et à mesure)*_
59 132 Etienne Pallier
60 132 Etienne Pallier
Voir le détail de la roadmap: https://projects.irap.omp.eu/projects/inventirap/roadmap
61 132 Etienne Pallier
62 128 Etienne Pallier
All steps below are to be understood with included refactoring, testing, and documenting (in code and on wiki),
63 128 Etienne Pallier
and updating of the Dashboard module
64 1 Etienne Pallier
65 126 Etienne Pallier
* Full Workflow based on Celery (starting from alert reception and until analysis) : 1 week
66 1 Etienne Pallier
67 128 Etienne Pallier
* AlertManager + RequestBuilder : 2-3 weeks
68 128 Etienne Pallier
69 126 Etienne Pallier
* Scheduler (to be integrated in this new architecture, and completed) : 1 week
70 124 Etienne Pallier
71 1 Etienne Pallier
* RoutineManager (+ RequestBuilder) : 2-3 weeks
72 124 Etienne Pallier
73 129 Etienne Pallier
* ObservationManager : 2-3 weeks
74 1 Etienne Pallier
75 124 Etienne Pallier
* AnalysisManager: 2 weeks
76 129 Etienne Pallier
77 1 Etienne Pallier
* Environment Monitoring : observation conditions, weather, site (PLC), and instruments status : 2 weeks
78 132 Etienne Pallier
79 132 Etienne Pallier
80 132 Etienne Pallier
81 132 Etienne Pallier
82 132 Etienne Pallier
|                    |  |_.Prévu |_.Réalisé |
83 135 Etienne Pallier
|/2=.S01 (14/3-18/3) |.1|/2=<."Version 0.1 - wiki + git + easy install (from script)":https://projects.irap.omp.eu/versions/53|/2=<.version 1.1|
84 132 Etienne Pallier
                     |.2|
85 135 Etienne Pallier
|/2=.S02 (21/3-25/3) |.1|/42=<."Version 0.2 - wiki + git + easy install (from script)":https://projects.irap.omp.eu/versions/53|_/42=<.version 0.2 (en cours...)|
86 132 Etienne Pallier
                     |.2|
87 135 Etienne Pallier
|/2=.S03 (28/3-01/4) |.1|
88 132 Etienne Pallier
                     |.2|
89 135 Etienne Pallier
|/2=.S04 (04/4-08/4) |.1|
90 132 Etienne Pallier
                     |.2|
91 135 Etienne Pallier
|/2=.S05 (11/4-15/4) |.1|
92 132 Etienne Pallier
                     |.2|
93 132 Etienne Pallier
|/2=.S06 (18/4-22/4) |.1|
94 135 Etienne Pallier
                     |.2|
95 132 Etienne Pallier
|/2=.S07 (25/4-29/4) |.1|
96 132 Etienne Pallier
                     |.2|
97 132 Etienne Pallier
|/2=.S08 (02/5-06/5) |.1|
98 135 Etienne Pallier
                     |.2|
99 139 Etienne Pallier
|/2=.S09 (09/5-13/5) |.1|
100 135 Etienne Pallier
                     |.2|
101 140 Etienne Pallier
|/2=.S10 (16/5-20/5) |.1|
102 132 Etienne Pallier
                     |.2|
103 141 Etienne Pallier
|/2=.S11 (23/5-27/5) |.1|
104 132 Etienne Pallier
                     |.2|
105 151 Etienne Pallier
|/2=.S12 (30/5-03/6) |.1|
106 135 Etienne Pallier
                     |.2|
107 134 Etienne Pallier
|/2=.S13 (06/6-10/6) |.1|
108 1 Etienne Pallier
                     |.2|
109 151 Etienne Pallier
|_/2=.S14 (13/6-17/6) |.1|
110 1 Etienne Pallier
                     |.2|
111 134 Etienne Pallier
|/2=.S15 (20/6-24/6) |.1|
112 134 Etienne Pallier
                     |.2|
113 134 Etienne Pallier
|/2=.S16 (27/6-01/7) |.1|
114 134 Etienne Pallier
                     |.2|
115 134 Etienne Pallier
|/2=.S17 (04/7-08/7) |.1|
116 134 Etienne Pallier
                     |.2|
117 134 Etienne Pallier
|/2=.S18 (11/7-15/7) |.1|
118 134 Etienne Pallier
                     |.2|
119 134 Etienne Pallier
|/2=.S19 (18/7-22/7) |.1|
120 134 Etienne Pallier
                     |.2|
121 134 Etienne Pallier
|/2=.S20 (25/7-29/7) |.1|
122 134 Etienne Pallier
                     |.2|
123 134 Etienne Pallier
|/2=.S21 (01/8-05/8) |.1|
124 134 Etienne Pallier
                     |.2|
125 134 Etienne Pallier
|/2=.S22 (08/8-12/8) |.1|
126 134 Etienne Pallier
                     |.2|
127 132 Etienne Pallier
128 132 Etienne Pallier
129 136 Etienne Pallier
130 132 Etienne Pallier
---
131 136 Etienne Pallier
132 136 Etienne Pallier
h2. %{margin-left:0px; font-weight:bold; font-size:25px;  display:block; color:red;}COMMIT PROCEDURE%
133 136 Etienne Pallier
134 136 Etienne Pallier
135 136 Etienne Pallier
Voici les différentes étapes à respecter au moment de chaque commit:
136 136 Etienne Pallier
137 136 Etienne Pallier
*1) S'assurer que tous les tests passent toujours...*
138 136 Etienne Pallier
139 153 Etienne Pallier
*2) Mettre à jour la version du ou des module(s) modifié(s)*
140 153 Etienne Pallier
(dans pyros/settings.py)
141 1 Etienne Pallier
142 152 Etienne Pallier
*3) Mettre à jour le fichier README (ceci est un exemple, un template)*
143 152 Etienne Pallier
144 136 Etienne Pallier
Date: 11/05/2016
145 137 Etienne Pallier
Version: 0.2.9
146 136 Etienne Pallier
Mise à jour doc install
147 136 Etienne Pallier
(Attention, changement structure BDD)
148 136 Etienne Pallier
Demande (terminée): https://projects.irap.omp.eu/issues/3542
149 137 Etienne Pallier
Version majeure en cours (0.2): https://projects.irap.omp.eu/versions/101
150 136 Etienne Pallier
151 136 Etienne Pallier
Remarques:
152 137 Etienne Pallier
=> Version: 0.2.9 = 9ème commit sur la version 0.2
153 136 Etienne Pallier
=> préciser "(bugfix)" si c'est le cas
154 136 Etienne Pallier
=> ajouter "(Attention, changement structure BDD)" s'il y a eu une modif de la BDD
155 136 Etienne Pallier
=> "Demande (terminée)" ou "Demande (en cours)", ou pas de demande du tout (exceptionnellement)
156 136 Etienne Pallier
=> ces infos permettront de savoir quelle version (et date) exacte du projet on a actuellement sur son disque
157 1 Etienne Pallier
158 136 Etienne Pallier
159 152 Etienne Pallier
*[4) Si c'est la fin d'une version majeure (0.1, 0.2, 0.3, ...)]*
160 136 Etienne Pallier
161 136 Etienne Pallier
* On doit normalement avoir écrit quelques nouveaux tests pour cette version !!!
162 136 Etienne Pallier
* Ajouter cette version en tête de la section "MAIN CHANGES (MILESTONES)" dans le fichier README
163 136 Etienne Pallier
* Mettre à jour la doc install/INSTALLATION à partir du wiki (si nécessaire)
164 1 Etienne Pallier
* Tester une installation du logiciel from scratch 
165 136 Etienne Pallier
166 136 Etienne Pallier
167 152 Etienne Pallier
*5) pull*
168 1 Etienne Pallier
169 136 Etienne Pallier
(au cas où quelqu'un d'autre aurait fait un push)
170 136 Etienne Pallier
171 136 Etienne Pallier
172 152 Etienne Pallier
*6) commit*
173 136 Etienne Pallier
174 136 Etienne Pallier
Reprendre dans le message de commit, faire un simple copier/coller des infos du fichier README (sauf date):
175 136 Etienne Pallier
176 136 Etienne Pallier
Version: 0.2.9
177 1 Etienne Pallier
Mise à jour doc install (bugfix)
178 136 Etienne Pallier
Demande (terminée): https://projects.irap.omp.eu/issues/3542
179 138 Etienne Pallier
Version majeure en cours (0.2): https://projects.irap.omp.eu/versions/101
180 136 Etienne Pallier
181 136 Etienne Pallier
182 152 Etienne Pallier
*[7) push]*
183 136 Etienne Pallier
184 136 Etienne Pallier
(seulement si le commit est important/urgent, ou suite à un ensemble de commits sur un même thème)
185 136 Etienne Pallier
186 122 Etienne Pallier
187 100 Etienne Pallier
---
188 3 Etienne Pallier
189 1 Etienne Pallier
h2. %{margin-left:0px; font-weight:bold; font-size:25px;  display:block; color:red;}DOCUMENTS%
190 1 Etienne Pallier
191 1 Etienne Pallier
192 101 Etienne Pallier
193 146 Etienne Pallier
* Module Planner (Scheduler) : https://projects.irap.omp.eu/attachments/download/2607/IRAP-OFT-CC-SP-0007.pdf
194 146 Etienne Pallier
195 146 Etienne Pallier
196 148 Etienne Pallier
* DOC Paul: https://drive.google.com/folderview?id=0BzmdbXGIqXXMQ3JMTWRyakJyVVU&usp=sharing_eid&ts=571a3c9d
197 148 Etienne Pallier
198 146 Etienne Pallier
* Grammaire (workflow pseudo code): https://docs.google.com/document/d/1wG8Ha8xzEiRdA1I76sN9Te4Gq2ehq48SzFjSTaYRhfA/edit
199 57 Etienne Pallier
200 56 Etienne Pallier
201 24 Etienne Pallier
---
202 3 Etienne Pallier
203 144 Etienne Pallier
h2. %{margin-left:0px; font-weight:bold; font-size:25px;  display:block; color:red;}OTHER USEFUL LINKS%
204 105 Etienne Pallier
205 105 Etienne Pallier
 * CADOR (A Klotz):
206 105 Etienne Pallier
207 106 Etienne Pallier
  * CADOR (portail de tous les telescopes) : http://cador.obs-hp.fr/ros/manual/cador_actions.html
208 106 Etienne Pallier
(click on "Manage", "CGI", or "Majordome")
209 106 Etienne Pallier
(or click on "Sequenced scenes" 1-5, each one is relative to a telescope underneath)
210 107 Etienne Pallier
(or click on "Rejected scenes" 1-5)
211 108 Etienne Pallier
  * Requests list: http://cador.obs-hp.fr/ros/manage/manage/liste_requete.php?hashuser=mdhxdjfu2scsrnfy2ry9
212 110 Etienne Pallier
  * Accès manuel: http://cador.obs-hp.fr/ros/manual
213 111 Etienne Pallier
  * Liste des scenes (sequences) TO BE PLANNED: http://cador.obs-hp.fr/ros/scenes_cador.php
214 70 Etienne Pallier
  * Historique des plannings : http://cador.obs-hp.fr/ros/sequenced/
215 119 Etienne Pallier
216 149 Etienne Pallier
 * VOEvent:
217 150 Etienne Pallier
218 149 Etienne Pallier
  * Protocole VTP: http://wiki.ivoa.net/twiki/bin/view/IVOA/VTPRFC
219 149 Etienne Pallier
220 119 Etienne Pallier
 * Celery: http://celery.readthedocs.org/en/latest/getting-started/first-steps-with-celery.html#first-steps
221 120 Etienne Pallier
222 121 Etienne Pallier
 * Created new user 'pyros' with password 'DjangoPyros'
223 70 Etienne Pallier
224 4 Etienne Pallier
 * pyrossu : pyrossu!
225 86 Etienne Pallier
226 86 Etienne Pallier
 * Alexandru work: https://projects.irap.omp.eu/projects/gft/wiki/Documentation_technique_projet#Fetch-the-project-from-github-via-git
227 71 Etienne Pallier
228 71 Etienne Pallier
 * readonly admin interface : https://gist.github.com/aaugustin/1388243
229 4 Etienne Pallier
230 4 Etienne Pallier
 * Liens vers web local :
231 4 Etienne Pallier
232 4 Etienne Pallier
  * homepage: http://localhost:8000
233 25 Etienne Pallier
  * admin: http://localhost:8000/admin
234 25 Etienne Pallier
235 26 Etienne Pallier
 * Eclipse:
236 26 Etienne Pallier
 
237 25 Etienne Pallier
  * Shift-Ctrl-f (ou Shift-Cmd-f) : reformatage du fichier selon PEP8
238 4 Etienne Pallier
  * Shift-Ctrl-1 : make doc string ...
239 4 Etienne Pallier
240 4 Etienne Pallier
 * Django:
241 80 Etienne Pallier
242 79 Etienne Pallier
  * Un répertoire de modules : https://www.djangopackages.com/
243 1 Etienne Pallier
  * Extensions
244 1 Etienne Pallier
245 83 Etienne Pallier
   * *django_jenkins* : intégration à Jenkins
246 83 Etienne Pallier
   * *factory_boy* : création de grappes de données pour les tests
247 83 Etienne Pallier
   
248 83 Etienne Pallier
    * https://factoryboy.readthedocs.org/en/latest/introduction.html
249 79 Etienne Pallier
    * https://factoryboy.readthedocs.org/en/latest/orms.html 
250 79 Etienne Pallier
251 79 Etienne Pallier
  * Modules très utilisés:
252 79 Etienne Pallier
253 79 Etienne Pallier
   * django_linaration_pagination : affichage de listes paginées
254 79 Etienne Pallier
   * django_sorting : affichage de tableaux triables
255 79 Etienne Pallier
   * django_breadcrumbs : création de fil d'ariane
256 79 Etienne Pallier
   * django_xworkflows : gestion de workflows
257 79 Etienne Pallier
   * easy_thumbnails : gestion de miniatures pour les images
258 38 Etienne Pallier
259 81 Etienne Pallier
  * Coding style: https://docs.djangoproject.com/en/dev/internals/contributing/writing-code/coding-style
260 82 Etienne Pallier
261 1 Etienne Pallier
  * Doc : *https://docs.djangoproject.com/fr (EN FRANCAIS)*
262 82 Etienne Pallier
263 82 Etienne Pallier
   * https://docs.djangoproject.com (EN)
264 72 Etienne Pallier
   * http://www.django-fr.org/planete
265 72 Etienne Pallier
   * https://docs.djangoproject.com/en/1.9/howto/deployment
266 72 Etienne Pallier
   * test fixtures : https://docs.djangoproject.com/en/1.9/howto/initial-data/
267 72 Etienne Pallier
   * managing static files: https://docs.djangoproject.com/en/1.9/howto/static-files/
268 72 Etienne Pallier
   * deploying static files: https://docs.djangoproject.com/en/1.9/howto/static-files/deployment/
269 72 Etienne Pallier
   * install on Windows: https://docs.djangoproject.com/en/1.9/howto/windows/
270 72 Etienne Pallier
   * writing migrations: https://docs.djangoproject.com/en/1.9/howto/writing-migrations/
271 72 Etienne Pallier
   * migrations : https://docs.djangoproject.com/en/1.9/topics/migrations/
272 1 Etienne Pallier
   * Django settings: https://docs.djangoproject.com/en/1.9/topics/settings/
273 72 Etienne Pallier
   * Testing: https://docs.djangoproject.com/en/1.9/topics/testing/
274 72 Etienne Pallier
   * User authentication: https://docs.djangoproject.com/en/1.9/topics/auth/
275 82 Etienne Pallier
276 82 Etienne Pallier
  * Autres ressources:
277 82 Etienne Pallier
278 82 Etienne Pallier
   * django-admin command: https://docs.djangoproject.com/en/1.9/ref/django-admin
279 82 Etienne Pallier
   * http://stackoverflow.com/questions/tagged/django
280 82 Etienne Pallier
   * https://www.djangopackages.com/
281 82 Etienne Pallier
   * http://forum.django-fr.org
282 44 Etienne Pallier
   * La mailing list : django@lists.afpy.org
283 44 Etienne Pallier
284 72 Etienne Pallier
285 4 Etienne Pallier
 * Image processing with Python : https://pillow.readthedocs.org/en/latest/handbook/overview.html
286 4 Etienne Pallier
287 19 Etienne Pallier
 * Git docs: 
288 4 Etienne Pallier
289 131 Etienne Pallier
  * From svn: https://git-scm.com/course/svn.html
290 4 Etienne Pallier
  * Permissions gitlab: https://gitlab.com/gitlab-org/gitlab-ce/blob/master/doc/permissions/permissions.md
291 4 Etienne Pallier
  * https://git-scm.com/docs
292 4 Etienne Pallier
  * https://git-scm.com/book/fr/v1/Les-bases-de-Git-Travailler-avec-des-d%C3%A9p%C3%B4ts-distants
293 15 Etienne Pallier
  * les workflows: https://aresu.dsi.cnrs.fr/spip.php?article219
294 4 Etienne Pallier
  * Git for Eclipse users : http://wiki.eclipse.org/EGit/Git_For_Eclipse_Users
295 4 Etienne Pallier
  * Git sur sourcesup (avec jenkins) : https://services.renater.fr/sourcesup/formation/chap04#gestion_d_un_projet_avec_git_jenkins_sonar_et_nexus
296 4 Etienne Pallier
297 4 Etienne Pallier
 * CADOR web interface: http://cador.obs-hp.fr/ros/manual/cador_actions.html
298 4 Etienne Pallier
299 4 Etienne Pallier
 * pylint (analyse de code) : https://www.pylint.org
300 4 Etienne Pallier
301 4 Etienne Pallier
 * pyreverse (uml diagrams generation, inclus dans pylint) : https://www.logilab.org/blogentry/6883
302 4 Etienne Pallier
303 4 Etienne Pallier
 * tox (a generic virtualenv management and test command line tool) : https://testrun.org/tox/latest/index.html
304 5 Etienne Pallier
305 5 Etienne Pallier
---
306 5 Etienne Pallier
307 5 Etienne Pallier
h2. %{margin-left:0px; font-weight:bold; font-size:25px;  display:block; color:red;}I - DATABASE SCHEMA (v0.2.1)%
308 5 Etienne Pallier
309 6 Etienne Pallier
310 7 Etienne Pallier
{{thumbnail(PYROS_PDM_v021.png, size=300, title=Pyros data model)}}
311 6 Etienne Pallier
312 7 Etienne Pallier
---
313 6 Etienne Pallier
314 20 Etienne Pallier
h2. %{margin-left:0px; font-weight:bold; font-size:25px;  display:block; color:red;}II - Get the project (from gitlab)%
315 20 Etienne Pallier
316 20 Etienne Pallier
h3. Gitlab management interface
317 20 Etienne Pallier
318 20 Etienne Pallier
https://gitlab.irap.omp.eu/epallier/pyros
319 20 Etienne Pallier
320 20 Etienne Pallier
https://gitlab.irap.omp.eu/epallier/pyros/team
321 6 Etienne Pallier
322 8 Etienne Pallier
h3. Get the project
323 8 Etienne Pallier
324 7 Etienne Pallier
https://projects.irap.omp.eu/projects/pyros/wiki/Project_Installation#II-Get-the-project-from-gitlab
325 7 Etienne Pallier
326 11 Etienne Pallier
---
327 11 Etienne Pallier
328 11 Etienne Pallier
h2. %{margin-left:0px; font-weight:bold; font-size:25px;  display:block; color:red;}III - INSTALLATION%
329 11 Etienne Pallier
330 11 Etienne Pallier
https://projects.irap.omp.eu/projects/pyros/wiki/Project_Installation#III-INSTALLATION
331 11 Etienne Pallier
332 6 Etienne Pallier
---
333 6 Etienne Pallier
334 6 Etienne Pallier
h2. %{margin-left:0px; font-weight:bold; font-size:25px;  display:block; color:red;}IV - CONFIGURATION of the Django Back Office (administration interface)%
335 6 Etienne Pallier
336 9 Etienne Pallier
[[django_backoffice_config|Configuration of the Django Back office (admin)]]
337 9 Etienne Pallier
338 13 Etienne Pallier
---
339 43 Etienne Pallier
340 1 Etienne Pallier
h2. %{margin-left:0px; font-weight:bold; font-size:25px;  display:block; color:red;}V - EVOLUTION OF THE PROJECT%
341 43 Etienne Pallier
342 43 Etienne Pallier
343 43 Etienne Pallier
344 43 Etienne Pallier
h3. Linking the User model to the django's one
345 43 Etienne Pallier
346 43 Etienne Pallier
* Modifications in models.py :
347 43 Etienne Pallier
348 43 Etienne Pallier
    * Rename User model to PyrosUser
349 43 Etienne Pallier
    * Rename user table name to pyros_user
350 43 Etienne Pallier
    * Change all occurences (User -> PyrosUser, users -> pyros_users, ...)
351 43 Etienne Pallier
    * from django.contrib.auth.models import User <== add at the beginning of the file
352 43 Etienne Pallier
    * user = models.OneToOneField(User, on_delete=models.CASCADE) <== add this field in PyrosUser declaration
353 43 Etienne Pallier
    * delete fields in PyrosUser : name, firstname, email, login, pass
354 43 Etienne Pallier
355 43 Etienne Pallier
* Modifications in admin.py :
356 43 Etienne Pallier
357 43 Etienne Pallier
    * Change all occurences (User* -> PyrosUser*, users -> pyros_users, ...)
358 43 Etienne Pallier
359 43 Etienne Pallier
<pre>
360 43 Etienne Pallier
$ python manage.py makemigrations pyrosapp
361 43 Etienne Pallier
$ python manage.py migrate
362 43 Etienne Pallier
</pre>
363 43 Etienne Pallier
364 43 Etienne Pallier
---
365 43 Etienne Pallier
366 41 Etienne Pallier
h3. Manage static files (for admin but also for each application)
367 41 Etienne Pallier
368 41 Etienne Pallier
./manage.py runserver
369 41 Etienne Pallier
370 41 Etienne Pallier
if DEBUG=False, we have errors, missing static files :
371 41 Etienne Pallier
372 41 Etienne Pallier
<pre>
373 41 Etienne Pallier
Not Found: /static/admin/css/base.css
374 41 Etienne Pallier
Not Found: /static/admin/css/login.css
375 41 Etienne Pallier
Not Found: /admin/login
376 41 Etienne Pallier
Not Found: /static/admin/css/base.css
377 41 Etienne Pallier
Not Found: /static/admin/css/login.css
378 41 Etienne Pallier
Not Found: /static/admin/css/base.css
379 41 Etienne Pallier
Not Found: /static/admin/css/login.css
380 41 Etienne Pallier
Not Found: /static/admin/css/base.css
381 41 Etienne Pallier
Not Found: /static/admin/css/dashboard.css
382 41 Etienne Pallier
Not Found: /static/admin/css/base.css
383 41 Etienne Pallier
Not Found: /static/admin/css/base.css
384 41 Etienne Pallier
385 41 Etienne Pallier
</pre>
386 41 Etienne Pallier
387 41 Etienne Pallier
388 41 Etienne Pallier
=> We have to activate the static files management
389 41 Etienne Pallier
390 41 Etienne Pallier
(see https://docs.djangoproject.com/en/1.9/howto/static-files)
391 41 Etienne Pallier
392 41 Etienne Pallier
In pyros/urls.py, add this:
393 41 Etienne Pallier
<pre>
394 41 Etienne Pallier
395 41 Etienne Pallier
from django.conf import settings
396 41 Etienne Pallier
from django.conf.urls.static import static
397 41 Etienne Pallier
398 41 Etienne Pallier
urlpatterns = [
399 41 Etienne Pallier
    url(r'^admin/', admin.site.urls),
400 41 Etienne Pallier
] + static(settings.STATIC_URL, document_root=settings.STATIC_ROOT)
401 41 Etienne Pallier
</pre>
402 41 Etienne Pallier
403 41 Etienne Pallier
STATIC_ROOT must be defined in settings and says where is the root of all static files
404 41 Etienne Pallier
405 41 Etienne Pallier
Edit settings.py, add:
406 41 Etienne Pallier
<pre>
407 41 Etienne Pallier
STATIC_ROOT = os.path.join(os.path.dirname(BASE_DIR), 'public', 'static')
408 41 Etienne Pallier
</pre>
409 41 Etienne Pallier
410 41 Etienne Pallier
411 41 Etienne Pallier
./manage.py collectstatic
412 41 Etienne Pallier
413 41 Etienne Pallier
=> 56 static files copied to '.../PYROS/public/static'
414 41 Etienne Pallier
415 41 Etienne Pallier
(in fact it is in public/static/admin/)
416 41 Etienne Pallier
417 41 Etienne Pallier
Cette commande copie tous les fichiers statiques de toutes les applis
418 41 Etienne Pallier
dans public/static
419 41 Etienne Pallier
420 41 Etienne Pallier
Apache viendra lire ce dossier unique
421 41 Etienne Pallier
422 41 Etienne Pallier
A chq changement d’un fichier statique d’une appli, exécuter « collectstatic » pour mettre à jour le dossier final public/static (auquel on ne doit pas toucher manuellement, c’est un dossier « final »)
423 41 Etienne Pallier
424 39 Etienne Pallier
425 39 Etienne Pallier
---
426 45 Etienne Pallier
427 45 Etienne Pallier
h2. %{margin-left:0px; font-weight:bold; font-size:25px;  display:block; color:red;}DJANGO SHELL (top cool)%
428 51 Etienne Pallier
429 51 Etienne Pallier
cf page 60 for the ORM methods
430 45 Etienne Pallier
431 45 Etienne Pallier
<pre>
432 45 Etienne Pallier
./manage.py shell
433 45 Etienne Pallier
Python 3.5.1 (default, Mar  2 2016, 03:38:02) 
434 46 Etienne Pallier
(InteractiveConsole)
435 45 Etienne Pallier
436 46 Etienne Pallier
>>> import django
437 45 Etienne Pallier
438 46 Etienne Pallier
>>> from pyrosapp.models import *
439 45 Etienne Pallier
440 45 Etienne Pallier
>>> country = Country(name='mexico', quota=1)
441 50 Etienne Pallier
>>> country.save()
442 50 Etienne Pallier
(ajout si pas d’id, modif si id)
443 45 Etienne Pallier
444 45 Etienne Pallier
>>> country = Country(name='france')
445 45 Etienne Pallier
>>> country.save()
446 45 Etienne Pallier
>>> country.pk
447 45 Etienne Pallier
>>> 2
448 45 Etienne Pallier
449 45 Etienne Pallier
>>> countries = Country.objects.all()
450 45 Etienne Pallier
>>> countries.count
451 45 Etienne Pallier
>>> <bound method QuerySet.count of <Country: mexico>, <Country: france>>
452 45 Etienne Pallier
>>> countries.count()
453 45 Etienne Pallier
>>> 2
454 45 Etienne Pallier
>>> print(countries)
455 45 Etienne Pallier
>>> <Country: mexico>, <Country: france>
456 45 Etienne Pallier
>>> print(countries.query)
457 45 Etienne Pallier
>>> SELECT country.id, country.name, country.desc, country.quota FROM country
458 45 Etienne Pallier
459 45 Etienne Pallier
>>> cs = countries.filter(name__icontains='fran')
460 45 Etienne Pallier
>>> print(cs)
461 45 Etienne Pallier
>>> <Country: france>
462 45 Etienne Pallier
463 45 Etienne Pallier
>>> cs = countries.filter(name__startswith='me')
464 45 Etienne Pallier
>>> print(cs)
465 45 Etienne Pallier
>>> <Country: mexico>
466 45 Etienne Pallier
467 45 Etienne Pallier
</pre>
468 45 Etienne Pallier
469 45 Etienne Pallier
470 45 Etienne Pallier
---
471 47 Etienne Pallier
472 47 Etienne Pallier
h2. %{margin-left:0px; font-weight:bold; font-size:25px;  display:block; color:red;}HOWTO (divers)%
473 64 Etienne Pallier
474 1 Etienne Pallier
h3. Models
475 64 Etienne Pallier
476 1 Etienne Pallier
1) Relationships between models (1-1, 1-N, N-M) (p55)
477 61 Etienne Pallier
478 61 Etienne Pallier
models.ManyToManyField : représente une relation de type N-N
479 1 Etienne Pallier
(peu importe de quel côté on le déclare)
480 61 Etienne Pallier
481 48 Etienne Pallier
models.OneToOneField : attention, le sens est important, on n’accèdera d’une table à l’autre que dans un sens
482 61 Etienne Pallier
483 61 Etienne Pallier
task <=> user
484 1 Etienne Pallier
task.user
485 64 Etienne Pallier
user.task_set
486 64 Etienne Pallier
487 64 Etienne Pallier
2) Quelques options pour les champs
488 64 Etienne Pallier
489 64 Etienne Pallier
Chaque type de champ possède ses propres propriétés. Cependant, certaines sont communes et souvent utilisées comme :
490 64 Etienne Pallier
491 64 Etienne Pallier
    verbose_name: label du champ
492 64 Etienne Pallier
    null : valeur NULL autorisée ou non en base de données
493 64 Etienne Pallier
    blank : valeur vide autorisée lors de la validation du champ dans un formulaire
494 64 Etienne Pallier
    default : valeur par défaut pour une nouvelle instance
495 64 Etienne Pallier
    editable : le champ doit-il apparaître automatiquement dans les formulaires
496 64 Etienne Pallier
    ...
497 64 Etienne Pallier
498 64 Etienne Pallier
499 47 Etienne Pallier
500 47 Etienne Pallier
501 47 Etienne Pallier
h3. Pour relier une appli python pure à un projet django :
502 47 Etienne Pallier
503 47 Etienne Pallier
=> Ajouter le src/ dans le pythonpath
504 47 Etienne Pallier
505 47 Etienne Pallier
506 47 Etienne Pallier
h3. Séparer le code métier :
507 47 Etienne Pallier
508 47 Etienne Pallier
=> installer le code métier comme un module via pip
509 47 Etienne Pallier
Couches :
510 47 Etienne Pallier
* présentation
511 47 Etienne Pallier
* métier
512 47 Etienne Pallier
* modèle
513 49 Etienne Pallier
514 49 Etienne Pallier
h3. ORM
515 49 Etienne Pallier
516 49 Etienne Pallier
(cf page 60)
517 59 Etienne Pallier
518 73 Etienne Pallier
<pre>
519 161 Etienne Pallier
520 161 Etienne Pallier
Exemple: Book
521 161 Etienne Pallier
===========================
522 161 Etienne Pallier
523 73 Etienne Pallier
b = Book(name='Two scoops of django',
524 1 Etienne Pallier
             release=date(2013, 08, 31))
525 73 Etienne Pallier
b.save()
526 73 Etienne Pallier
=> ajout car pas d’id, 
527 74 Etienne Pallier
528 74 Etienne Pallier
b.name ='Two scoops of django - Best practices'
529 1 Etienne Pallier
b.save()
530 74 Etienne Pallier
=> modif car il y a un id
531 74 Etienne Pallier
532 1 Etienne Pallier
b.delete()
533 75 Etienne Pallier
534 49 Etienne Pallier
Toutes les instances:
535 49 Etienne Pallier
Book.objects.all()
536 75 Etienne Pallier
537 59 Etienne Pallier
Liste filtrée:
538 49 Etienne Pallier
books = Book.objects.filter(
539 49 Etienne Pallier
        release__gte=date(2013, 01, 01)
540 49 Etienne Pallier
      ).exclude(
541 49 Etienne Pallier
        borrowed=True
542 49 Etienne Pallier
      )
543 1 Etienne Pallier
544 161 Etienne Pallier
Attention, la requete est exécutée le plus tard possible, seulement quand django a vraiment besoin de l’exécuter
545 75 Etienne Pallier
546 49 Etienne Pallier
Liste ordonnée:
547 49 Etienne Pallier
books = Book.objects.exclude(borrowed=True).order_by('title')
548 75 Etienne Pallier
print (books.author)
549 49 Etienne Pallier
550 77 Etienne Pallier
Une instance précise:
551 75 Etienne Pallier
Book.objects.get(pk=12)
552 77 Etienne Pallier
553 1 Etienne Pallier
554 1 Etienne Pallier
555 1 Etienne Pallier
556 162 Etienne Pallier
557 161 Etienne Pallier
Liens vers objets associés:
558 161 Etienne Pallier
===========================
559 161 Etienne Pallier
560 77 Etienne Pallier
Retrouver les livres disponibles d'un auteur :
561 77 Etienne Pallier
>> author = Author.objects.get(pk=25)
562 1 Etienne Pallier
>> author.books.filter(borrowed=False)
563 1 Etienne Pallier
(books est le related name déclaré dans la relation manytomany)
564 77 Etienne Pallier
565 75 Etienne Pallier
566 77 Etienne Pallier
Ajouter un livre à une catégorie :
567 77 Etienne Pallier
>> category = Category.objects.get(pk=5)
568 77 Etienne Pallier
>> book = Book.objects.get(pk=12)
569 75 Etienne Pallier
>> category.books.add(book)
570 75 Etienne Pallier
571 1 Etienne Pallier
Supprimer l'association de livres à une catégorie :
572 1 Etienne Pallier
>> category = Category.objects.get(pk=5)
573 77 Etienne Pallier
>> category.books.clear()
574 161 Etienne Pallier
575 161 Etienne Pallier
</pre>
576 47 Etienne Pallier
577 53 Etienne Pallier
---
578 53 Etienne Pallier
579 53 Etienne Pallier
h3. Serveur Web
580 104 Paul Carensac
581 157 Etienne Pallier
<pre>
582 157 Etienne Pallier
583 104 Paul Carensac
Passer sur le port 80 :
584 104 Paul Carensac
585 104 Paul Carensac
venv_py35_pyros ==> lib ==> python3.5 ==> site-packages ==> django ==> core ==> management ==> commands
586 104 Paul Carensac
Edit runserver.py and change "default_port"
587 104 Paul Carensac
588 53 Etienne Pallier
589 53 Etienne Pallier
Apache : gère tous les fichiers statiques (images, html…), et délègue les fichiers python au serveur django
590 53 Etienne Pallier
591 53 Etienne Pallier
Moteur web django sera soit du wsgi soit du unicorn
592 53 Etienne Pallier
Par défaut, 1 seul worker, mais on peut en configurer plusieurs,
593 53 Etienne Pallier
l’idéal étant de faire nb coeurs + 1 (le worker maître qui fait le dispatching aux autres)
594 53 Etienne Pallier
595 53 Etienne Pallier
Frontend : Apache ou Ngininx
596 53 Etienne Pallier
Backend : gunicorn (gère facilement des workers) ou uwsgi
597 53 Etienne Pallier
598 53 Etienne Pallier
==> gunicorn library.wsgi
599 53 Etienne Pallier
(à la place de manage runserver ==> A EVITER EN PROD)
600 53 Etienne Pallier
601 53 Etienne Pallier
pip install gunicorn
602 53 Etienne Pallier
603 53 Etienne Pallier
gunicorn library.wsgi
604 53 Etienne Pallier
ou
605 53 Etienne Pallier
gunicorn - - workers 5 library.wsgi
606 53 Etienne Pallier
607 156 Etienne Pallier
(gunicorn est un équivalent de tomcat, c'est un serveur d’appli Python)
608 53 Etienne Pallier
609 53 Etienne Pallier
1) URL arrive à Apache, qui dispatche (il gère seul les fichiers statiques, et les fichiers python il les transmet à Django)
610 53 Etienne Pallier
2) le fichier library/urls.py prend le relai pour tout ce qui est django
611 65 Etienne Pallier
612 65 Etienne Pallier
613 65 Etienne Pallier
*On peut ajouter un fichier urls.py pour gérer les urls de l’appli
614 65 Etienne Pallier
(on garde le urls.py général du projet pour gérer les grandes urls):*
615 157 Etienne Pallier
616 157 Etienne Pallier
</pre>
617 157 Etienne Pallier
618 1 Etienne Pallier
619 66 Etienne Pallier
620 66 Etienne Pallier
<pre>
621 65 Etienne Pallier
Déclaration d'une URL
622 65 Etienne Pallier
623 65 Etienne Pallier
# books/urls.py
624 65 Etienne Pallier
from django.conf.urls import patterns, include, url
625 65 Etienne Pallier
urlpatterns = [
626 65 Etienne Pallier
    url(r'^book_list$', 'books.views.book_list', name='book_list'),
627 65 Etienne Pallier
]
628 65 Etienne Pallier
629 65 Etienne Pallier
Inclusion des URLs de l'application au projet
630 65 Etienne Pallier
631 65 Etienne Pallier
# library/urls.py
632 65 Etienne Pallier
...
633 65 Etienne Pallier
urlpatterns = [
634 65 Etienne Pallier
    ...
635 1 Etienne Pallier
    url(r'^books/', include('books.urls', namespace='books')),
636 60 Etienne Pallier
]
637 60 Etienne Pallier
638 60 Etienne Pallier
</pre>
639 60 Etienne Pallier
640 60 Etienne Pallier
h3. MTV design pattern
641 60 Etienne Pallier
642 60 Etienne Pallier
643 60 Etienne Pallier
MTV == MVC :
644 60 Etienne Pallier
645 60 Etienne Pallier
Model = Model
646 60 Etienne Pallier
Template = View
647 60 Etienne Pallier
View = Controller
648 60 Etienne Pallier
649 60 Etienne Pallier
650 60 Etienne Pallier
CREATION DE LA VUE (en fait, le controleur) : slide 23
651 60 Etienne Pallier
views.py = CONTROLEUR
652 60 Etienne Pallier
653 60 Etienne Pallier
654 60 Etienne Pallier
Template = LA VUE (slide 24)
655 60 Etienne Pallier
(on peut user Jinja à la place du moteur django par défaut)
656 60 Etienne Pallier
657 60 Etienne Pallier
Dans chq appli, on crée un dossier templates/ et un sous-dossier du nom de l’appli/
658 60 Etienne Pallier
(==> todo/templates/todo/)
659 60 Etienne Pallier
660 60 Etienne Pallier
Même principe pour les fichiers statiques :
661 60 Etienne Pallier
src/static/appli1, appli2, appli3…
662 60 Etienne Pallier
663 60 Etienne Pallier
NOMENCLATURE template :
664 60 Etienne Pallier
nommodèle_action.html
665 60 Etienne Pallier
(ex: book_list.html)
666 60 Etienne Pallier
667 60 Etienne Pallier
*On pourrait tout mettre dans le urls.py du projet, MAIS c’est mieux
668 60 Etienne Pallier
de créer un fichier urls.py PAR APPLI, puis de les inclure dans le fichier urls.py principal*
669 60 Etienne Pallier
670 60 Etienne Pallier
Class-based views ==> classes controleurs
671 60 Etienne Pallier
Les méthodes get() et post() sont déjà définies, et on peut les surcharger…
672 60 Etienne Pallier
673 60 Etienne Pallier
Avec un template (gabarit), on peut générer autre chose que du html,
674 60 Etienne Pallier
on peut par ex générer du texte, du pdf, un email, un xml…
675 60 Etienne Pallier
676 60 Etienne Pallier
677 60 Etienne Pallier
678 60 Etienne Pallier
Vue liste (et détail) :
679 60 Etienne Pallier
https://docs.djangoproject.com/fr/1.8/topics/class-based-views/generic-display/
680 60 Etienne Pallier
1) todo/views.py
681 60 Etienne Pallier
from django.views.generic import ListView
682 60 Etienne Pallier
from books.models import Publisher
683 60 Etienne Pallier
684 60 Etienne Pallier
class PublisherList(ListView):
685 60 Etienne Pallier
    model = Publisher
686 60 Etienne Pallier
687 60 Etienne Pallier
688 60 Etienne Pallier
2) todolist/urls.py
689 60 Etienne Pallier
from django.conf.urls import url
690 60 Etienne Pallier
from books.views import PublisherList
691 60 Etienne Pallier
692 60 Etienne Pallier
urlpatterns = [
693 60 Etienne Pallier
    url(r'^publishers/$', PublisherList.as_view()),
694 60 Etienne Pallier
]
695 60 Etienne Pallier
696 60 Etienne Pallier
3) todo/templates/todo/
697 60 Etienne Pallier
698 60 Etienne Pallier
699 60 Etienne Pallier
700 53 Etienne Pallier
- Vue Liste : par défaut le template reçoit un objet « objects_list »
701 53 Etienne Pallier
- Vue détail : object (on peut faire object.pk, …)
702 53 Etienne Pallier
703 53 Etienne Pallier
704 53 Etienne Pallier
705 40 Etienne Pallier
---
706 87 Etienne Pallier
707 87 Etienne Pallier
h2. %{margin-left:0px; font-weight:bold; font-size:25px;  display:block; color:red;}USEFUL TOOLS FOR DEV%
708 88 Etienne Pallier
709 159 Etienne Pallier
710 159 Etienne Pallier
711 159 Etienne Pallier
712 159 Etienne Pallier
---
713 159 Etienne Pallier
714 169 Quentin Durand
h2. *+PlantUML+*
715 159 Etienne Pallier
716 159 Etienne Pallier
Pour créer des diagrammes UML à la volée, à partir d'un fichier texte, au fur et à mesure de la frappe
717 1 Etienne Pallier
718 1 Etienne Pallier
719 168 Quentin Durand
1) Prérequis : il faut installer graphviz :
720 159 Etienne Pallier
721 168 Quentin Durand
$ sudo apt-get install graphviz (ubuntu, debian)
722 1 Etienne Pallier
723 169 Quentin Durand
$ sudo yum install graphviz) (fedora)
724 1 Etienne Pallier
725 169 Quentin Durand
*Pour PyCharm*
726 159 Etienne Pallier
727 169 Quentin Durand
 -télécharger plugin : https://plugins.jetbrains.com/plugin/7017-plantuml-integration
728 168 Quentin Durand
  
729 169 Quentin Durand
 -extraire les deux .jar dans le dossier /bin de pycharm : ex= /opt/pycharm-community-2017.2.3/bin/ si pycharm est dans /opt
730 168 Quentin Durand
 
731 170 Quentin Durand
 Pour ouvrir une fenêtre plantUML : View -> Tool Windows -> PlantUML
732 1 Etienne Pallier
733 1 Etienne Pallier
734 169 Quentin Durand
*Pour Eclipse*
735 159 Etienne Pallier
736 168 Quentin Durand
1) Installer le plugin : Menu Help/Install New Software... 
737 159 Etienne Pallier
738 168 Quentin Durand
Entrer l'adresse suivante, et sélectionner PlantUML
739 168 Quentin Durand
740 168 Quentin Durand
http://plantuml.sourceforge.net/updatesitejuno/
741 168 Quentin Durand
742 168 Quentin Durand
2) Créer un graphique UML
743 159 Etienne Pallier
744 159 Etienne Pallier
- Créer un fichier texte (voir exemple ci-dessous)
745 159 Etienne Pallier
746 159 Etienne Pallier
- Window/Show View/Other/Plantuml
747 159 Etienne Pallier
748 159 Etienne Pallier
=> le diagramme doit alors s'afficher
749 159 Etienne Pallier
750 159 Etienne Pallier
751 159 Etienne Pallier
752 159 Etienne Pallier
753 159 Etienne Pallier
754 88 Etienne Pallier
---
755 96 Etienne Pallier
756 95 Etienne Pallier
h3. Pyreverse (included in pylint) : useful for generating uml class diagrams
757 1 Etienne Pallier
758 96 Etienne Pallier
https://www.logilab.org/blogentry/6883
759 96 Etienne Pallier
760 96 Etienne Pallier
<pre>
761 96 Etienne Pallier
$ cd PYROS/
762 96 Etienne Pallier
763 96 Etienne Pallier
$ pyreverse -o png -p pyrosapp -a 1 -A src/pyrosapp/
764 96 Etienne Pallier
765 97 Etienne Pallier
$ pyreverse -o png -p pyrosapp -s 1 -S src/pyrosapp/
766 97 Etienne Pallier
767 96 Etienne Pallier
$ pyreverse -ASmy -k -o png -p pyrosappadmin src/pyrosapp/admin.py
768 1 Etienne Pallier
</pre>
769 99 Etienne Pallier
770 99 Etienne Pallier
{{thumbnail(classes_pyrosapp.png, size=300)}}
771 99 Etienne Pallier
{{thumbnail(classes_pyrosappadmin.png, size=300)}}
772 99 Etienne Pallier
{{thumbnail(classes_dashboard.png, size=300)}}
773 98 Etienne Pallier
774 98 Etienne Pallier
775 89 Etienne Pallier
h3. django-extensions and graphviz : useful for generating an image of all the models and their relationships
776 91 Etienne Pallier
777 89 Etienne Pallier
{{thumbnail(models.png, size=300, title=Pyros data model)}}
778 90 Etienne Pallier
779 89 Etienne Pallier
django-extensions: http://django-extensions.readthedocs.org/en/latest/installation_instructions.html
780 92 Etienne Pallier
781 92 Etienne Pallier
GraphViz (development) installation :
782 92 Etienne Pallier
783 92 Etienne Pallier
<pre>
784 92 Etienne Pallier
MacOS with macport:
785 92 Etienne Pallier
$ sudo port install graphviz-devel
786 92 Etienne Pallier
787 92 Etienne Pallier
Ubuntu:
788 92 Etienne Pallier
$ sudo apt-get install graphviz-dev
789 92 Etienne Pallier
790 92 Etienne Pallier
Windows:
791 92 Etienne Pallier
Download it
792 92 Etienne Pallier
</pre>
793 93 Etienne Pallier
794 1 Etienne Pallier
Python pygraphviz package installation:
795 92 Etienne Pallier
<pre>
796 1 Etienne Pallier
$ pip install pygraphviz
797 1 Etienne Pallier
=> errors on MacOS (using macport) : "fatal error: 'graphviz/cgraph.h' file not found"
798 93 Etienne Pallier
=> $ pip install --install-option="--include-path=/opt/local/include"  --install-option="--library-path=/opt/local/lib" pygraphviz
799 1 Etienne Pallier
</pre>
800 93 Etienne Pallier
801 93 Etienne Pallier
Python django-extensions package installation:
802 93 Etienne Pallier
<pre>
803 93 Etienne Pallier
$ pip install django-bootstrap3
804 93 Etienne Pallier
$ pip install django-extensions
805 93 Etienne Pallier
($ pip install --upgrade django-extensions)
806 92 Etienne Pallier
</pre>
807 93 Etienne Pallier
808 93 Etienne Pallier
Generate the image:
809 93 Etienne Pallier
<pre>
810 92 Etienne Pallier
$ cd src/
811 93 Etienne Pallier
$ python manage.py graph_models -a -g -o models.png
812 92 Etienne Pallier
</pre>
813 89 Etienne Pallier
814 89 Etienne Pallier
---
815 6 Etienne Pallier
816 6 Etienne Pallier
h2. %{margin-left:0px; font-weight:bold; font-size:25px;  display:block; color:red;}INSTALLATION FROM THE BEGINNING (for dev only, history of the initial project creation)%
817 1 Etienne Pallier
818 1 Etienne Pallier
819 1 Etienne Pallier
[[pyros_install_from_start|Pyros installation from the beginning]]