taskjuggler 3.1.0 → 3.2.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (410) hide show
  1. data/CHANGELOG +44 -0
  2. data/bin/tj3webd +4 -0
  3. data/data/css/tjreport.css +14 -5
  4. data/data/tjp.vim +22 -7
  5. data/examples/Fedora-20/reports.tji +2 -4
  6. data/examples/Scrum/Product Burndown.csv +26 -0
  7. data/examples/Scrum/Sprint 1 Burndown.csv +26 -0
  8. data/examples/Scrum/Sprint 2 Burndown.csv +26 -0
  9. data/examples/Scrum/Sprint 3 Burndown.csv +26 -0
  10. data/examples/Scrum/scrum.tjp +141 -0
  11. data/examples/Tutorial/tutorial.tjp +13 -7
  12. data/lib/taskjuggler/Attributes.rb +2 -3
  13. data/lib/taskjuggler/HTMLDocument.rb +25 -18
  14. data/lib/taskjuggler/Journal.rb +85 -65
  15. data/lib/taskjuggler/KeywordDocumentation.rb +25 -13
  16. data/lib/taskjuggler/LeaveList.rb +1 -1
  17. data/lib/taskjuggler/Limits.rb +3 -5
  18. data/lib/taskjuggler/MessageHandler.rb +173 -19
  19. data/lib/taskjuggler/Painter.rb +75 -0
  20. data/lib/taskjuggler/Painter/BasicShapes.rb +76 -0
  21. data/lib/taskjuggler/Painter/Color.rb +273 -0
  22. data/lib/taskjuggler/Painter/Element.rb +56 -0
  23. data/lib/taskjuggler/Painter/FontData.rb +221 -0
  24. data/lib/taskjuggler/Painter/FontMetrics.rb +125 -0
  25. data/lib/taskjuggler/Painter/FontMetricsData.rb +151 -0
  26. data/lib/taskjuggler/Painter/Group.rb +77 -0
  27. data/lib/taskjuggler/Painter/Points.rb +47 -0
  28. data/lib/taskjuggler/Painter/Primitives.rb +100 -0
  29. data/lib/taskjuggler/Painter/SVGSupport.rb +36 -0
  30. data/lib/taskjuggler/Painter/Text.rb +36 -0
  31. data/lib/taskjuggler/Project.rb +46 -29
  32. data/lib/taskjuggler/ProjectFileParser.rb +24 -22
  33. data/lib/taskjuggler/ProjectFileScanner.rb +2 -2
  34. data/lib/taskjuggler/PropertyTreeNode.rb +26 -34
  35. data/lib/taskjuggler/Query.rb +8 -5
  36. data/lib/taskjuggler/RealFormat.rb +3 -0
  37. data/lib/taskjuggler/Resource.rb +3 -5
  38. data/lib/taskjuggler/ResourceScenario.rb +19 -7
  39. data/lib/taskjuggler/RichText.rb +4 -6
  40. data/lib/taskjuggler/RichText/FunctionExample.rb +1 -1
  41. data/lib/taskjuggler/RichText/FunctionHandler.rb +5 -6
  42. data/lib/taskjuggler/RichText/Parser.rb +4 -6
  43. data/lib/taskjuggler/RichText/RTFNavigator.rb +1 -1
  44. data/lib/taskjuggler/RichText/RTFQuery.rb +2 -3
  45. data/lib/taskjuggler/RichText/RTFReport.rb +1 -1
  46. data/lib/taskjuggler/RichText/RTFReportLink.rb +1 -2
  47. data/lib/taskjuggler/RichText/RTFWithQuerySupport.rb +1 -1
  48. data/lib/taskjuggler/RichText/Scanner.rb +6 -6
  49. data/lib/taskjuggler/RichText/Snip.rb +1 -2
  50. data/lib/taskjuggler/RuntimeConfig.rb +9 -6
  51. data/lib/taskjuggler/ScenarioData.rb +4 -3
  52. data/lib/taskjuggler/Scoreboard.rb +6 -0
  53. data/lib/taskjuggler/SheetHandlerBase.rb +25 -8
  54. data/lib/taskjuggler/SimpleQueryExpander.rb +14 -5
  55. data/lib/taskjuggler/SyntaxReference.rb +1 -2
  56. data/lib/taskjuggler/TableColumnSorter.rb +84 -0
  57. data/lib/taskjuggler/Task.rb +3 -5
  58. data/lib/taskjuggler/TaskJuggler.rb +36 -29
  59. data/lib/taskjuggler/TaskScenario.rb +154 -66
  60. data/lib/taskjuggler/TextParser.rb +24 -17
  61. data/lib/taskjuggler/TextParser/Scanner.rb +16 -11
  62. data/lib/taskjuggler/TextParser/SourceFileInfo.rb +20 -15
  63. data/lib/taskjuggler/TimeSheets.rb +6 -12
  64. data/lib/taskjuggler/Tj3AppBase.rb +35 -16
  65. data/lib/taskjuggler/Tj3Config.rb +1 -1
  66. data/lib/taskjuggler/TjpSyntaxRules.rb +239 -49
  67. data/lib/taskjuggler/XMLElement.rb +9 -2
  68. data/lib/taskjuggler/apps/Tj3.rb +43 -37
  69. data/lib/taskjuggler/apps/Tj3Client.rb +62 -112
  70. data/lib/taskjuggler/apps/Tj3Daemon.rb +66 -29
  71. data/lib/taskjuggler/apps/Tj3Man.rb +5 -5
  72. data/lib/taskjuggler/apps/Tj3SsReceiver.rb +10 -13
  73. data/lib/taskjuggler/apps/Tj3SsSender.rb +13 -16
  74. data/lib/taskjuggler/apps/Tj3TsReceiver.rb +10 -13
  75. data/lib/taskjuggler/apps/Tj3TsSender.rb +12 -15
  76. data/lib/taskjuggler/apps/Tj3TsSummary.rb +12 -15
  77. data/lib/taskjuggler/apps/Tj3WebD.rb +99 -0
  78. data/lib/taskjuggler/daemon/Daemon.rb +50 -10
  79. data/lib/taskjuggler/daemon/DaemonConnector.rb +127 -0
  80. data/lib/taskjuggler/daemon/ProcessIntercom.rb +36 -21
  81. data/lib/taskjuggler/daemon/ProjectBroker.rb +122 -112
  82. data/lib/taskjuggler/daemon/ProjectServer.rb +78 -46
  83. data/lib/taskjuggler/daemon/ReportServer.rb +52 -28
  84. data/lib/taskjuggler/daemon/ReportServlet.rb +92 -21
  85. data/lib/taskjuggler/daemon/WebServer.rb +75 -22
  86. data/lib/taskjuggler/daemon/WelcomePage.rb +1 -0
  87. data/lib/taskjuggler/reports/AccountListRE.rb +3 -3
  88. data/lib/taskjuggler/reports/CSVFile.rb +9 -2
  89. data/lib/taskjuggler/reports/ChartPlotter.rb +453 -0
  90. data/lib/taskjuggler/reports/Navigator.rb +1 -0
  91. data/lib/taskjuggler/reports/NikuReport.rb +4 -4
  92. data/lib/taskjuggler/reports/Report.rb +6 -18
  93. data/lib/taskjuggler/reports/ReportBase.rb +9 -9
  94. data/lib/taskjuggler/reports/ReportContext.rb +2 -2
  95. data/lib/taskjuggler/reports/StatusSheetReport.rb +6 -6
  96. data/lib/taskjuggler/reports/TableReport.rb +24 -15
  97. data/lib/taskjuggler/reports/TimeSheetReport.rb +5 -5
  98. data/lib/taskjuggler/reports/TraceReport.rb +251 -0
  99. data/lib/tj3webd.rb +17 -0
  100. data/manual/Day_To_Day_Juggling +10 -3
  101. data/manual/Installation +38 -19
  102. data/manual/Software +25 -19
  103. data/manual/Tutorial +119 -110
  104. data/manual/html/Day_To_Day_Juggling.html +7 -5
  105. data/manual/html/Getting_Started.html +4 -4
  106. data/manual/html/How_To_Contribute.html +4 -4
  107. data/manual/html/Installation.html +19 -11
  108. data/manual/html/Intro.html +4 -4
  109. data/manual/html/Reporting_Bugs.html +4 -4
  110. data/manual/html/Rich_Text_Attributes.html +4 -4
  111. data/manual/html/Software.html +15 -11
  112. data/manual/html/TaskJuggler_2x_Migration.html +4 -4
  113. data/manual/html/TaskJuggler_Internals.html +4 -4
  114. data/manual/html/The_TaskJuggler_Syntax.html +4 -4
  115. data/manual/html/Tutorial.html +41 -32
  116. data/manual/html/account.html +4 -4
  117. data/manual/html/account.task.html +4 -4
  118. data/manual/html/accountprefix.html +4 -4
  119. data/manual/html/accountreport.html +27 -9
  120. data/manual/html/accountroot.html +5 -5
  121. data/manual/html/active.html +4 -4
  122. data/manual/html/adopt.task.html +4 -4
  123. data/manual/html/aggregate.html +4 -4
  124. data/manual/html/alert.html +4 -4
  125. data/manual/html/alertlevels.html +4 -4
  126. data/manual/html/allocate.html +5 -5
  127. data/manual/html/alphabet.html +4 -4
  128. data/manual/html/alternative.html +4 -4
  129. data/manual/html/author.html +4 -4
  130. data/manual/html/balance.html +5 -5
  131. data/manual/html/booking.resource.html +4 -4
  132. data/manual/html/booking.task.html +4 -4
  133. data/manual/html/caption.html +5 -5
  134. data/manual/html/cellcolor.column.html +43 -8
  135. data/manual/html/celltext.column.html +4 -4
  136. data/manual/html/center.html +5 -5
  137. data/manual/html/charge.html +4 -4
  138. data/manual/html/chargeset.html +4 -4
  139. data/manual/html/columnid.html +27 -15
  140. data/manual/html/columns.html +5 -5
  141. data/manual/html/complete.html +4 -4
  142. data/manual/html/copyright.html +4 -4
  143. data/manual/html/credits.html +4 -4
  144. data/manual/html/css/tjreport.css +14 -5
  145. data/manual/html/currency.html +4 -4
  146. data/manual/html/currencyformat.html +5 -5
  147. data/manual/html/dailymax.html +5 -5
  148. data/manual/html/dailymin.html +5 -5
  149. data/manual/html/dailyworkinghours.html +4 -4
  150. data/manual/html/date.extend.html +4 -4
  151. data/manual/html/date.html +5 -5
  152. data/manual/html/definitions.html +4 -4
  153. data/manual/html/depends.html +4 -4
  154. data/manual/html/details.html +4 -4
  155. data/manual/html/disabled.html +4 -4
  156. data/manual/html/duration.html +4 -4
  157. data/manual/html/efficiency.html +4 -4
  158. data/manual/html/effort.html +4 -4
  159. data/manual/html/email.html +4 -4
  160. data/manual/html/enabled.html +4 -4
  161. data/manual/html/end.column.html +4 -4
  162. data/manual/html/end.html +4 -4
  163. data/manual/html/end.limit.html +4 -4
  164. data/manual/html/end.report.html +5 -5
  165. data/manual/html/end.timesheet.html +4 -4
  166. data/manual/html/endcredit.html +4 -4
  167. data/manual/html/epilog.html +5 -5
  168. data/manual/html/export.html +4 -4
  169. data/manual/html/extend.html +4 -4
  170. data/manual/html/fail.html +43 -8
  171. data/manual/html/fdl.html +4 -4
  172. data/manual/html/flags.account.html +4 -4
  173. data/manual/html/flags.html +4 -4
  174. data/manual/html/flags.journalentry.html +4 -4
  175. data/manual/html/flags.report.html +5 -5
  176. data/manual/html/flags.resource.html +4 -4
  177. data/manual/html/flags.statussheet.html +4 -4
  178. data/manual/html/flags.task.html +4 -4
  179. data/manual/html/flags.timesheet.html +4 -4
  180. data/manual/html/fontcolor.column.html +43 -8
  181. data/manual/html/footer.html +5 -5
  182. data/manual/html/formats.html +5 -5
  183. data/manual/html/functions.html +4 -4
  184. data/manual/html/gapduration.html +4 -4
  185. data/manual/html/gaplength.html +4 -4
  186. data/manual/html/halign.center.html +4 -4
  187. data/manual/html/halign.column.html +43 -8
  188. data/manual/html/halign.left.html +4 -4
  189. data/manual/html/halign.right.html +4 -4
  190. data/manual/html/hasalert.html +4 -4
  191. data/manual/html/header.html +5 -5
  192. data/manual/html/headline.html +7 -7
  193. data/manual/html/height.html +72 -0
  194. data/manual/html/hideaccount.html +46 -11
  195. data/manual/html/hidejournalentry.html +5 -5
  196. data/manual/html/hidereport.html +43 -8
  197. data/manual/html/hideresource.html +44 -9
  198. data/manual/html/hidetask.html +44 -9
  199. data/manual/html/icalreport.html +4 -4
  200. data/manual/html/include.macro.html +4 -4
  201. data/manual/html/include.project.html +4 -4
  202. data/manual/html/include.properties.html +4 -4
  203. data/manual/html/index.html +2 -1
  204. data/manual/html/inherit.extend.html +4 -4
  205. data/manual/html/interval1.html +4 -4
  206. data/manual/html/interval2.html +4 -4
  207. data/manual/html/interval3.html +4 -4
  208. data/manual/html/interval4.html +4 -4
  209. data/manual/html/isactive.html +4 -4
  210. data/manual/html/ischildof.html +4 -4
  211. data/manual/html/isdependencyof.html +4 -4
  212. data/manual/html/isdutyof.html +4 -4
  213. data/manual/html/isfeatureof.html +4 -4
  214. data/manual/html/isleaf.html +4 -4
  215. data/manual/html/ismilestone.html +4 -4
  216. data/manual/html/isongoing.html +4 -4
  217. data/manual/html/isresource.html +4 -4
  218. data/manual/html/isresponsibilityof.html +4 -4
  219. data/manual/html/istask.html +4 -4
  220. data/manual/html/journalattributes.html +11 -7
  221. data/manual/html/journalentry.html +4 -4
  222. data/manual/html/journalmode.html +5 -5
  223. data/manual/html/leaveallowance.html +5 -5
  224. data/manual/html/leaves.html +5 -6
  225. data/manual/html/left.html +5 -5
  226. data/manual/html/length.html +4 -4
  227. data/manual/html/limits.allocate.html +4 -4
  228. data/manual/html/limits.html +4 -4
  229. data/manual/html/limits.resource.html +4 -4
  230. data/manual/html/limits.task.html +4 -4
  231. data/manual/html/listitem.column.html +4 -4
  232. data/manual/html/listtype.column.html +4 -4
  233. data/manual/html/loadunit.html +5 -5
  234. data/manual/html/logicalexpression.html +8 -44
  235. data/manual/html/logicalflagexpression.html +4 -4
  236. data/manual/html/macro.html +4 -4
  237. data/manual/html/managers.html +4 -4
  238. data/manual/html/mandatory.html +4 -4
  239. data/manual/html/maxend.html +4 -4
  240. data/manual/html/maximum.html +5 -5
  241. data/manual/html/maxstart.html +4 -4
  242. data/manual/html/milestone.html +4 -4
  243. data/manual/html/minend.html +4 -4
  244. data/manual/html/minimum.html +5 -5
  245. data/manual/html/minstart.html +4 -4
  246. data/manual/html/monthlymax.html +5 -5
  247. data/manual/html/monthlymin.html +5 -5
  248. data/manual/html/navbar.html +10 -4
  249. data/manual/html/navigator.html +4 -4
  250. data/manual/html/newtask.html +4 -4
  251. data/manual/html/nikureport.html +4 -4
  252. data/manual/html/note.task.html +4 -4
  253. data/manual/html/now.html +4 -4
  254. data/manual/html/numberformat.html +5 -5
  255. data/manual/html/onend.html +4 -4
  256. data/manual/html/onstart.html +4 -4
  257. data/manual/html/opennodes.html +5 -5
  258. data/manual/html/overtime.booking.html +4 -4
  259. data/manual/html/period.column.html +4 -4
  260. data/manual/html/period.limit.html +4 -4
  261. data/manual/html/period.report.html +5 -5
  262. data/manual/html/period.task.html +4 -4
  263. data/manual/html/persistent.html +4 -4
  264. data/manual/html/precedes.html +4 -4
  265. data/manual/html/priority.html +4 -4
  266. data/manual/html/priority.timesheet.html +4 -4
  267. data/manual/html/project.html +4 -4
  268. data/manual/html/projectid.html +4 -4
  269. data/manual/html/projectid.task.html +4 -4
  270. data/manual/html/projectids.html +4 -4
  271. data/manual/html/projection.html +5 -7
  272. data/manual/html/prolog.html +5 -5
  273. data/manual/html/properties.html +11 -5
  274. data/manual/html/purge.html +5 -5
  275. data/manual/html/rate.html +4 -4
  276. data/manual/html/rate.resource.html +4 -4
  277. data/manual/html/reference.extend.html +4 -4
  278. data/manual/html/remaining.html +4 -4
  279. data/manual/html/replace.html +4 -4
  280. data/manual/html/reportprefix.html +4 -4
  281. data/manual/html/resource.html +4 -10
  282. data/manual/html/resourceattributes.html +4 -4
  283. data/manual/html/resourceprefix.html +4 -4
  284. data/manual/html/resourcereport.html +28 -10
  285. data/manual/html/resourceroot.html +5 -5
  286. data/manual/html/resources.limit.html +4 -4
  287. data/manual/html/responsible.html +4 -4
  288. data/manual/html/richtext.extend.html +4 -4
  289. data/manual/html/right.html +5 -5
  290. data/manual/html/rollupaccount.html +44 -9
  291. data/manual/html/rollupresource.html +44 -9
  292. data/manual/html/rolluptask.html +44 -9
  293. data/manual/html/scale.column.html +4 -4
  294. data/manual/html/scenario.html +4 -22
  295. data/manual/html/scenario.ical.html +4 -4
  296. data/manual/html/scenarios.export.html +4 -4
  297. data/manual/html/scenarios.html +5 -5
  298. data/manual/html/scenariospecific.extend.html +4 -4
  299. data/manual/html/scheduled.html +4 -4
  300. data/manual/html/scheduling.html +4 -4
  301. data/manual/html/select.html +4 -4
  302. data/manual/html/selfcontained.html +5 -5
  303. data/manual/html/shift.allocate.html +4 -4
  304. data/manual/html/shift.html +4 -4
  305. data/manual/html/shift.resource.html +5 -5
  306. data/manual/html/shift.task.html +4 -4
  307. data/manual/html/shift.timesheet.html +4 -4
  308. data/manual/html/shifts.allocate.html +4 -4
  309. data/manual/html/shifts.resource.html +4 -4
  310. data/manual/html/shifts.task.html +4 -4
  311. data/manual/html/shorttimeformat.html +4 -4
  312. data/manual/html/sloppy.booking.html +4 -4
  313. data/manual/html/sloppy.projection.html +5 -5
  314. data/manual/html/sortaccounts.html +5 -5
  315. data/manual/html/sortjournalentries.html +5 -5
  316. data/manual/html/sortresources.html +5 -5
  317. data/manual/html/sorttasks.html +5 -5
  318. data/manual/html/start.column.html +4 -4
  319. data/manual/html/start.html +4 -4
  320. data/manual/html/start.limit.html +4 -4
  321. data/manual/html/start.report.html +5 -5
  322. data/manual/html/startcredit.html +4 -4
  323. data/manual/html/status.statussheet.html +4 -4
  324. data/manual/html/status.timesheet.html +4 -4
  325. data/manual/html/statussheet.html +4 -4
  326. data/manual/html/statussheetreport.html +4 -4
  327. data/manual/html/strict.projection.html +5 -5
  328. data/manual/html/summary.html +4 -4
  329. data/manual/html/supplement.html +4 -4
  330. data/manual/html/supplement.resource.html +4 -10
  331. data/manual/html/supplement.task.html +4 -28
  332. data/manual/html/tagfile.html +4 -4
  333. data/manual/html/task.html +4 -28
  334. data/manual/html/task.statussheet.html +4 -4
  335. data/manual/html/task.timesheet.html +4 -4
  336. data/manual/html/taskattributes.html +4 -4
  337. data/manual/html/taskprefix.html +4 -4
  338. data/manual/html/taskreport.html +28 -10
  339. data/manual/html/taskroot.html +5 -5
  340. data/manual/html/text.extend.html +4 -4
  341. data/manual/html/textreport.html +27 -9
  342. data/manual/html/timeformat.html +5 -5
  343. data/manual/html/timeoff.nikureport.html +4 -4
  344. data/manual/html/timesheet.html +4 -4
  345. data/manual/html/timesheetreport.html +23 -5
  346. data/manual/html/timezone.export.html +4 -4
  347. data/manual/html/timezone.html +4 -4
  348. data/manual/html/timezone.report.html +5 -5
  349. data/manual/html/timezone.shift.html +4 -4
  350. data/manual/html/timingresolution.html +4 -4
  351. data/manual/html/title.column.html +4 -4
  352. data/manual/html/title.html +5 -5
  353. data/manual/html/toc.html +207 -179
  354. data/manual/html/tooltip.column.html +45 -10
  355. data/manual/html/tracereport.html +405 -0
  356. data/manual/html/trackingscenario.html +6 -6
  357. data/manual/html/treelevel.html +4 -4
  358. data/manual/html/vacation.html +4 -4
  359. data/manual/html/vacation.resource.html +4 -4
  360. data/manual/html/vacation.shift.html +4 -4
  361. data/manual/html/warn.html +43 -8
  362. data/manual/html/weeklymax.html +5 -5
  363. data/manual/html/weeklymin.html +5 -5
  364. data/manual/html/weekstartsmonday.html +4 -4
  365. data/manual/html/weekstartssunday.html +6 -6
  366. data/manual/html/width.column.html +6 -6
  367. data/manual/html/width.html +72 -0
  368. data/manual/html/work.html +4 -4
  369. data/manual/html/workinghours.project.html +4 -4
  370. data/manual/html/workinghours.resource.html +4 -4
  371. data/manual/html/workinghours.shift.html +4 -4
  372. data/manual/html/yearlyworkingdays.html +4 -4
  373. data/spec/Color_spec.rb +60 -0
  374. data/spec/ProjectBroker_spec.rb +3 -2
  375. data/spec/StatusSheets_spec.rb +5 -4
  376. data/spec/TableColumnSorter_spec.rb +78 -0
  377. data/spec/TimeSheets_spec.rb +6 -2
  378. data/spec/Tj3Daemon_spec.rb +2 -2
  379. data/spec/TraceReport_spec.rb +117 -0
  380. data/taskjuggler.gemspec +1 -1
  381. data/test/MessageChecker.rb +3 -1
  382. data/test/ReferenceGenerator.rb +1 -1
  383. data/test/TestSuite/CSV-Reports/Leave.tjp +1 -1
  384. data/test/TestSuite/CSV-Reports/refs/resourcereport_with_tasks.csv +3 -0
  385. data/test/TestSuite/CSV-Reports/refs/taskcounter.csv +9 -0
  386. data/test/TestSuite/CSV-Reports/refs/taskreport_with_resources.csv +19 -16
  387. data/test/TestSuite/CSV-Reports/refs/weekly.csv +1 -0
  388. data/test/TestSuite/Export-Reports/refs/LogicalExpression.tjp +14 -2
  389. data/test/TestSuite/Export-Reports/refs/tutorial.tjp +98 -86
  390. data/test/TestSuite/Scheduler/Correct/Leaves.tjp +25 -0
  391. data/test/TestSuite/Syntax/Correct/Leave.tjp +1 -1
  392. data/test/TestSuite/Syntax/Correct/LogicalExpression.tjp +9 -1
  393. data/test/TestSuite/Syntax/Correct/TraceReport.tjp +10 -0
  394. data/test/TestSuite/Syntax/Correct/tutorial.tjp +10 -4
  395. data/test/test_CSV-Reports.rb +3 -3
  396. data/test/test_Export-Reports.rb +91 -86
  397. data/test/test_Journal.rb +15 -12
  398. data/test/test_Limits.rb +3 -3
  399. data/test/test_Project.rb +1 -2
  400. data/test/test_ProjectFileScanner.rb +1 -1
  401. data/test/test_PropertySet.rb +1 -1
  402. data/test/test_Query.rb +5 -6
  403. data/test/test_ReportGenerator.rb +15 -7
  404. data/test/test_RichText.rb +4 -3
  405. data/test/test_Scheduler.rb +19 -7
  406. data/test/test_ShiftAssignments.rb +2 -2
  407. data/test/test_SimpleQueryExpander.rb +29 -2
  408. data/test/test_Syntax.rb +14 -5
  409. metadata +49 -10
  410. data/lib/taskjuggler/LogFile.rb +0 -73
@@ -31,13 +31,10 @@ class TaskJuggler
31
31
 
32
32
  include TjpSyntaxRules
33
33
 
34
- # Create the parser object. _messageHandler_ is a TjMessageHandler that is
35
- # used for error reporting.
36
- def initialize(messageHandler)
34
+ # Create the parser object.
35
+ def initialize
37
36
  super
38
37
 
39
- @tjMessageHandler = messageHandler
40
-
41
38
  # Define the token types that the ProjectFileScanner may return for
42
39
  # variable elements.
43
40
  @variables = [ :INTEGER, :FLOAT, :DATE, :TIME, :STRING, :LITERAL,
@@ -52,7 +49,7 @@ class TaskJuggler
52
49
  # Call this function with the master file to start processing a TJP file or
53
50
  # a set of TJP files.
54
51
  def open(file, master, fileNameIsBuffer = false)
55
- @scanner = ProjectFileScanner.new(file, @messageHandler)
52
+ @scanner = ProjectFileScanner.new(file)
56
53
  # We need the ProjectFileScanner object for error reporting.
57
54
  if master && !fileNameIsBuffer && file != '.' && file[-4, 4] != '.tjp'
58
55
  error('illegal_extension', "Project file name must end with " +
@@ -216,22 +213,19 @@ class TaskJuggler
216
213
  # variable tokens, a subset can be provided by _tokenSet_.
217
214
  def newRichText(text, sfi, tokenSet = nil)
218
215
  rText = RichText.new(text, RTFHandlers.create(@project, sfi))
219
- unless (rti = rText.generateIntermediateFormat( [ 0, 0, 0], tokenSet))
220
- rText.messageHandler.messages.each do |msg|
221
- # Map the SourceFileInfo of the RichText back to the original
222
- # location in the input file.
223
- sfi = TextParser::SourceFileInfo.new(
224
- sfi.fileName, sfi.lineNo + msg.sourceFileInfo.lineNo - 1, 0)
225
- # Then replay the error message.
226
- @messageHandler.addMessage(msg.type, msg.id, msg.message, sfi,
227
- msg.line)
228
- end
229
- end
230
- rti.sectionNumbers = false
216
+ # The RichText is processed by a separate parser. Messages will not have
217
+ # the proper source file info unless we baseline them with the original
218
+ # source file info.
219
+ mh = MessageHandlerInstance.instance
220
+ mh.baselineSFI = sfi
221
+ rti = rText.generateIntermediateFormat( [ 0, 0, 0 ], tokenSet)
222
+ # Reset the baseline again.
223
+ mh.baselineSFI = nil
224
+ rti.sectionNumbers = false if rti
231
225
  rti
232
226
  end
233
227
 
234
- # This method is a convenience wrapper around Project.new. It checks if
228
+ # This method is a convenience wrapper around Report.new. It checks if
235
229
  # the report name already exists. It also triggers the attribute
236
230
  # inheritance. +name+ is the name of the report, +type+ is the report
237
231
  # type. +sourceFileInfo+ is a SourceFileInfo of the report definition. The
@@ -432,8 +426,12 @@ class TaskJuggler
432
426
  # Determine the title of the column with the ID _colId_. The title may be
433
427
  # from the static set or be from a user defined attribute.
434
428
  def columnTitle(colId)
435
- TableReport.defaultColumnTitle(colId) ||
436
- @project.attributeName(colId)
429
+ if @property.typeSpec == :tracereport
430
+ "<-id->:<-scenario->.#{colId}"
431
+ else
432
+ TableReport.defaultColumnTitle(colId) ||
433
+ @project.attributeName(colId)
434
+ end
437
435
  end
438
436
 
439
437
 
@@ -485,7 +483,11 @@ class TaskJuggler
485
483
  end
486
484
  # The << operator does not set the 'provided' flag. Just do a self
487
485
  # assignment to trigget the flag to get set.
488
- @property[attrId, @scenarioIdx] = @property[attrId, @scenarioIdx]
486
+ begin
487
+ @property[attrId, @scenarioIdx] = @property[attrId, @scenarioIdx]
488
+ rescue AttributeOverwrite
489
+ # Overwrites are ok here.
490
+ end
489
491
  end
490
492
 
491
493
  end
@@ -19,7 +19,7 @@ class TaskJuggler
19
19
  # of the TJP syntax.
20
20
  class ProjectFileScanner < TextParser::Scanner
21
21
 
22
- def initialize(masterFile, messageHandler)
22
+ def initialize(masterFile)
23
23
  tokenPatterns = [
24
24
  # Any white spaces
25
25
  [ nil, /\s+/, :tjp, method('newPos') ],
@@ -150,7 +150,7 @@ class TaskJuggler
150
150
  [ :LITERAL, /./ ]
151
151
  ]
152
152
 
153
- super(masterFile, messageHandler, Log, tokenPatterns, :tjp)
153
+ super(masterFile, Log, tokenPatterns, :tjp)
154
154
  end
155
155
 
156
156
  private
@@ -11,6 +11,8 @@
11
11
  # published by the Free Software Foundation.
12
12
  #
13
13
 
14
+ require 'taskjuggler/MessageHandler'
15
+
14
16
  class TaskJuggler
15
17
 
16
18
  # This class is the base object for all Project properties. A Project property
@@ -27,6 +29,8 @@ class TaskJuggler
27
29
  # attribute like an URL that contains more details about the task.
28
30
  class PropertyTreeNode
29
31
 
32
+ include MessageHandler
33
+
30
34
  attr_reader :propertySet, :id, :subId, :parent, :project, :sequenceNo,
31
35
  :children, :adoptees
32
36
  attr_accessor :name, :sourceFileInfo
@@ -363,11 +367,18 @@ class TaskJuggler
363
367
  end
364
368
 
365
369
  # Return a list with all parent nodes of this node.
366
- def ancestors
370
+ def ancestors(includeStepParents = false)
367
371
  nodes = []
368
- n = self
369
- while n.parent
370
- nodes << (n = n.parent)
372
+ if includeStepParents
373
+ parents.each do |parent|
374
+ nodes << parent
375
+ nodes += parent.ancestors(true)
376
+ end
377
+ else
378
+ n = self
379
+ while n.parent
380
+ nodes << (n = n.parent)
381
+ end
371
382
  end
372
383
  nodes
373
384
  end
@@ -554,16 +565,14 @@ class TaskJuggler
554
565
  def query_alert(query)
555
566
  journal = @project['journal']
556
567
  query.sortable = query.numerical = alert =
557
- journal.alertLevel(query.end, self, query.hideJournalEntry)
568
+ journal.alertLevel(query.end, self, query)
558
569
  alertLevel = @project['alertLevels'][alert]
559
570
  query.string = alertLevel.name
560
571
  rText = "<fcol:#{alertLevel.color}><nowiki>#{alertLevel.name}" +
561
572
  "</nowiki></fcol>"
562
- unless (rti = RichText.new(rText, RTFHandlers.create(@project),
563
- @project.messageHandler).
564
- generateIntermediateFormat)
565
- @project.messageHandler.warning('ptn_journal',
566
- "Syntax error in journal message")
573
+ unless (rti = RichText.new(rText, RTFHandlers.create(@project)).
574
+ generateIntermediateFormat)
575
+ warning('ptn_journal', "Syntax error in journal message")
567
576
  return nil
568
577
  end
569
578
  rti.blockMode = false
@@ -572,15 +581,13 @@ class TaskJuggler
572
581
 
573
582
  def query_alertmessages(query)
574
583
  journalMessages(@project['journal'].alertEntries(query.end, self, 1,
575
- query.start,
576
- query.hideJournalEntry),
584
+ query.start, query),
577
585
  query, true)
578
586
  end
579
587
 
580
588
  def query_alertsummaries(query)
581
589
  journalMessages(@project['journal'].alertEntries(query.end, self, 1,
582
- query.start,
583
- query.hideJournalEntry),
590
+ query.start, query),
584
591
  query, false)
585
592
  end
586
593
 
@@ -600,8 +607,8 @@ class TaskJuggler
600
607
 
601
608
  def query_alerttrend(query)
602
609
  journal = @project['journal']
603
- startAlert = journal.alertLevel(query.start, self, query.hideJournalEntry)
604
- endAlert = journal.alertLevel(query.end, self, query.hideJournalEntry)
610
+ startAlert = journal.alertLevel(query.start, self, query)
611
+ endAlert = journal.alertLevel(query.end, self, query)
605
612
  if startAlert < endAlert
606
613
  query.sortable = 0
607
614
  query.string = 'Up'
@@ -653,19 +660,6 @@ class TaskJuggler
653
660
  @data[scenarioIdx].send(func, *args, &block)
654
661
  end
655
662
 
656
- def error(id, text)
657
- @project.messageHandler.error(id, text, @sourceFileInfo, nil, self, nil)
658
- end
659
-
660
- def warning(id, text)
661
- @project.messageHandler.warning(id, text, @sourceFileInfo, nil, self, nil)
662
- end
663
-
664
- def info(id, text)
665
- @project.messageHandler.info(id, text, @sourceFileInfo, nil, self, nil)
666
- end
667
-
668
-
669
663
  private
670
664
 
671
665
  # Create a blog-style list of all alert messages that match the Query.
@@ -693,11 +687,9 @@ class TaskJuggler
693
687
  end
694
688
  # Now convert the RichText markup String into RichTextIntermediate
695
689
  # format.
696
- unless (rti = RichText.new(rText, RTFHandlers.create(@project),
697
- @project.messageHandler).
698
- generateIntermediateFormat)
699
- @project.messageHandler.warning('ptn_journal',
700
- "Syntax error in journal message")
690
+ unless (rti = RichText.new(rText, RTFHandlers.create(@project)).
691
+ generateIntermediateFormat)
692
+ warning('ptn_journal', "Syntax error in journal message")
701
693
  return nil
702
694
  end
703
695
  # No section numbers, please!
@@ -325,15 +325,19 @@ class TaskJuggler
325
325
  # should not exceed. nil means no limit. Never use quarters since it's
326
326
  # pretty uncommon to use.
327
327
  max = [ 60, 48, nil, 8, 24, 0, nil ]
328
+ stdFormat = RealFormat.new([ '-', '', '', '.',
329
+ @numberFormat.fractionDigits ])
328
330
 
329
331
  i = 0
332
+ fSep = @numberFormat.fractionSeparator
330
333
  factors.each do |factor|
331
334
  scaledValue = value * factor
332
335
  str = @numberFormat.format(scaledValue)
333
- delta[i] = ((scaledValue - str.to_f).abs * 1000).to_i
336
+ stdStr = stdFormat.format(scaledValue)
337
+ delta[i] = (scaledValue - stdStr.to_f).abs
334
338
  # We ignore results that are 0 or exceed the maximum. To ensure that
335
339
  # we have at least one result the unscaled value is always taken.
336
- if (factor != 1.0 && /^[0.]*$/ =~ str) ||
340
+ if (factor != 1.0 && /^[0.]*$/ =~ stdStr) ||
337
341
  (max[i] && scaledValue > max[i])
338
342
  options << nil
339
343
  else
@@ -346,13 +350,12 @@ class TaskJuggler
346
350
  # the default if all values have the same length.
347
351
  shortest = 2
348
352
  delta.length.times do |j|
349
- shortest = j if options[j] && options[j][0, 2] != '0.' &&
350
- delta[j] <= delta[shortest]
353
+ shortest = j if options[j] && delta[j] < delta[shortest]
351
354
  end
352
355
 
353
356
  # Find the shortest option.
354
357
  6.times do |j|
355
- shortest = j if options[j] && options[j][0, 2] != '0.' &&
358
+ shortest = j if options[j] && options[j][0, 2] != '0' + fSep &&
356
359
  options[j].length < options[shortest].length
357
360
  end
358
361
 
@@ -27,6 +27,9 @@ class TaskJuggler
27
27
  # fractionDigits: Number of fractional digits to show. (Fixnum)
28
28
  class RealFormat
29
29
 
30
+ attr_reader :signPrefix, :signSuffix, :thousandsSeparator,
31
+ :fractionSeparator, :fractionDigits
32
+
30
33
  # Create a new RealFormat object and define the formating rules.
31
34
  def initialize(args)
32
35
  iVars = %w( @signPrefix @signSuffix @thousandsSeparator
@@ -85,11 +85,9 @@ class TaskJuggler
85
85
 
86
86
  # Now convert the RichText markup String into RichTextIntermediate
87
87
  # format.
88
- unless (rti = RichText.new(rText, RTFHandlers.create(@project),
89
- @project.messageHandler).
90
- generateIntermediateFormat)
91
- @project.messageHandler.warning(
92
- 'res_dashboard', 'Syntax error in dashboard text')
88
+ unless (rti = RichText.new(rText, RTFHandlers.create(@project)).
89
+ generateIntermediateFormat)
90
+ warning('res_dashboard', 'Syntax error in dashboard text')
93
91
  return nil
94
92
  end
95
93
  # No section numbers, please!
@@ -136,11 +136,18 @@ class TaskJuggler
136
136
  resource.finishScheduling(@scenarioIdx)
137
137
  end
138
138
 
139
- if (parent = @property.parent)
140
- # Add the assigned task to the parent duties list.
139
+ # Add the parent tasks of each task to the duties list.
140
+ @duties.each do |task|
141
+ task.ancestors(true).each do |pTask|
142
+ @duties << pTask unless @duties.include?(pTask)
143
+ end
144
+ end
145
+
146
+ # Add the assigned task to the parent(s) resource duties list.
147
+ @property.parents.each do |pResource|
141
148
  @duties.each do |task|
142
- unless parent['duties', @scenarioIdx].include?(task)
143
- parent['duties', @scenarioIdx] << task
149
+ unless pResource['duties', @scenarioIdx].include?(task)
150
+ pResource['duties', @scenarioIdx] << task
144
151
  end
145
152
  end
146
153
  end
@@ -434,8 +441,11 @@ class TaskJuggler
434
441
 
435
442
 
436
443
  # Returns the work of the resource (and its children) weighted by their
437
- # efficiency.
444
+ # efficiency. If _task_ is provided, only the work for this task and all
445
+ # its sub tasks are being counted.
438
446
  def getEffectiveWork(startIdx, endIdx, task = nil)
447
+ # Make sure we have the real Task and not a proxy.
448
+ task = task.ptn if task
439
449
  # There can't be any effective work if the start is after the end or the
440
450
  # todo list doesn't contain the specified task.
441
451
  return 0.0 if startIdx >= endIdx || (task && !@duties.include?(task))
@@ -632,7 +642,8 @@ class TaskJuggler
632
642
  end
633
643
 
634
644
  # Count the booked slots between the start and end index. If _task_ is not
635
- # nil count only those slots that are assigned to this particular task.
645
+ # nil count only those slots that are assigned to this particular task or
646
+ # any of its sub tasks.
636
647
  def getAllocatedSlots(startIdx, endIdx, task)
637
648
  # If there is no scoreboard, we don't have any allocations.
638
649
  return 0 unless @scoreboard
@@ -641,8 +652,9 @@ class TaskJuggler
641
652
  return 0 if startIdx >= endIdx
642
653
 
643
654
  bookedSlots = 0
655
+ taskList = task ? task.all : []
644
656
  @scoreboard.each(startIdx, endIdx) do |slot|
645
- if (task.nil? && slot.is_a?(Task)) || (task && slot == task)
657
+ if slot.is_a?(Task) && (task.nil? || taskList.include?(slot))
646
658
  bookedSlots += 1
647
659
  end
648
660
  end
@@ -72,7 +72,7 @@ class TaskJuggler
72
72
  #
73
73
  class RichText
74
74
 
75
- attr_reader :inputText, :messageHandler
75
+ attr_reader :inputText
76
76
 
77
77
  # The Parser uses complex to setup data structures that are identical for
78
78
  # all RichText instances. So, we'll share them across the instances.
@@ -83,11 +83,10 @@ class TaskJuggler
83
83
  # case an error occurs, an exception of type TjException will be raised.
84
84
  # _functionHandlers_ is a Hash that maps RichTextFunctionHandler objects
85
85
  # by their function name.
86
- def initialize(text, functionHandlers = [], messageHandler = nil)
86
+ def initialize(text, functionHandlers = [])
87
87
  # Keep a copy of the original text.
88
88
  @inputText = text
89
89
  @functionHandlers = functionHandlers
90
- @messageHandler = messageHandler || MessageHandler.new
91
90
  end
92
91
 
93
92
  # Convert the @inputText into an abstract syntax tree that can then be
@@ -103,11 +102,10 @@ class TaskJuggler
103
102
  # We'll setup the RichTextParser once and share it across all instances.
104
103
  if @@parser
105
104
  # We already have a RichTextParser that we can reuse.
106
- @@parser.reuse(@messageHandler, rti, sectionCounter, tokenSet)
105
+ @@parser.reuse(rti, sectionCounter, tokenSet)
107
106
  else
108
107
  # There is no RichTextParser yet, create one.
109
- @@parser = RichTextParser.new(@messageHandler, rti, sectionCounter,
110
- tokenSet)
108
+ @@parser = RichTextParser.new(rti, sectionCounter, tokenSet)
111
109
  end
112
110
 
113
111
  @@parser.open(@inputText)
@@ -23,7 +23,7 @@ class TaskJuggler
23
23
  class RichTextFunctionExample < RichTextFunctionHandler
24
24
 
25
25
  def initialize
26
- super(nil, 'example')
26
+ super('example')
27
27
  @blockFunction = true
28
28
  end
29
29
 
@@ -11,6 +11,8 @@
11
11
  # published by the Free Software Foundation.
12
12
  #
13
13
 
14
+ require 'taskjuggler/MessageHandler'
15
+
14
16
  class TaskJuggler
15
17
 
16
18
  # This class is the abstract base class for all RichText function handlers.
@@ -24,19 +26,16 @@ class TaskJuggler
24
26
  # second is the argument Array.
25
27
  class RichTextFunctionHandler
26
28
 
29
+ include MessageHandler
30
+
27
31
  attr_reader :function, :blockFunction
28
32
 
29
- def initialize(messageHandler, function, sourceFileInfo = nil)
30
- @messageHandler = messageHandler
33
+ def initialize(function, sourceFileInfo = nil)
31
34
  @function = function
32
35
  @blockFunction = false
33
36
  @sourceFileInfo = sourceFileInfo
34
37
  end
35
38
 
36
- def error(id, text)
37
- @messageHandler.error(id, text, @sourceFileInfo) if @messageHandler
38
- end
39
-
40
39
  end
41
40
 
42
41
  end
@@ -29,9 +29,8 @@ class TaskJuggler
29
29
 
30
30
  # Create the parser and initialize the rule set. _rt_ is the RichText object
31
31
  # the resulting tree of RichTextElement objects should belong to.
32
- def initialize(messageHandler, rti, sectionCounter = [ 0, 0, 0, 0 ],
33
- tokenSet = nil)
34
- super(messageHandler)
32
+ def initialize(rti, sectionCounter = [ 0, 0, 0, 0 ], tokenSet = nil)
33
+ super()
35
34
  @richTextI = rti
36
35
  # These are the tokens that can be returned by the RichTextScanner.
37
36
  @variables = [ :LINEBREAK, :SPACE, :WORD,
@@ -56,12 +55,11 @@ class TaskJuggler
56
55
  @numberListCounter = [ 0, 0, 0, 0 ]
57
56
  end
58
57
 
59
- def reuse(messageHandler, rti, sectionCounter = [ 0, 0, 0, 0],
58
+ def reuse(rti, sectionCounter = [ 0, 0, 0, 0],
60
59
  tokenSet = nil)
61
60
  @blockedVariables = {}
62
61
  @stack = nil
63
62
  @richTextI = rti
64
- @messageHandler = messageHandler
65
63
  @sectionCounter = sectionCounter
66
64
  limitTokenSet(tokenSet)
67
65
  end
@@ -70,7 +68,7 @@ class TaskJuggler
70
68
  def open(text)
71
69
  # Make sure that the last line is properly terminated with a newline.
72
70
  # Multiple newlines at the end are simply ignored.
73
- @scanner = RichTextScanner.new(text + "\n\n", @messageHandler, Log)
71
+ @scanner = RichTextScanner.new(text + "\n\n", Log)
74
72
  @scanner.open(true)
75
73
  end
76
74