pygments.rb 0.6.3 → 1.0.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +7 -0
- data/CHANGELOG.md +11 -0
- data/README.md +6 -6
- data/Rakefile +2 -1
- data/cache-lexers.rb +1 -1
- data/circle.yml +7 -0
- data/lib/pygments/lexer.rb +3 -3
- data/lib/pygments/popen.rb +67 -30
- data/lib/pygments/version.rb +1 -1
- data/pygments.rb.gemspec +2 -1
- data/test/test_pygments.rb +16 -16
- data/vendor/pygments-main/AUTHORS +54 -8
- data/vendor/pygments-main/CHANGES +247 -25
- data/vendor/pygments-main/LICENSE +1 -1
- data/vendor/pygments-main/Makefile +15 -6
- data/vendor/pygments-main/README.rst +39 -0
- data/vendor/pygments-main/REVISION +1 -1
- data/vendor/pygments-main/TODO +0 -3
- data/vendor/pygments-main/doc/_themes/pygments14/layout.html +1 -1
- data/vendor/pygments-main/doc/_themes/pygments14/static/pygments14.css_t +1 -1
- data/vendor/pygments-main/doc/conf.py +3 -11
- data/vendor/pygments-main/doc/docs/api.rst +15 -0
- data/vendor/pygments-main/doc/docs/cmdline.rst +6 -2
- data/vendor/pygments-main/doc/docs/filterdevelopment.rst +4 -3
- data/vendor/pygments-main/doc/docs/integrate.rst +11 -15
- data/vendor/pygments-main/doc/docs/java.rst +7 -7
- data/vendor/pygments-main/doc/docs/lexerdevelopment.rst +258 -171
- data/vendor/pygments-main/doc/docs/lexers.rst +2 -2
- data/vendor/pygments-main/doc/docs/styles.rst +58 -0
- data/vendor/pygments-main/doc/docs/tokens.rst +22 -2
- data/vendor/pygments-main/doc/docs/unicode.rst +15 -7
- data/vendor/pygments-main/doc/faq.rst +17 -21
- data/vendor/pygments-main/doc/index.rst +12 -11
- data/vendor/pygments-main/doc/languages.rst +10 -7
- data/vendor/pygments-main/external/autopygmentize +9 -6
- data/vendor/pygments-main/external/lasso-builtins-generator-9.lasso +70 -52
- data/vendor/pygments-main/external/markdown-processor.py +1 -1
- data/vendor/pygments-main/external/moin-parser.py +1 -1
- data/vendor/pygments-main/external/rst-directive.py +1 -1
- data/vendor/pygments-main/pygmentize +2 -1
- data/vendor/pygments-main/pygments/__init__.py +14 -15
- data/vendor/pygments-main/pygments/cmdline.py +188 -113
- data/vendor/pygments-main/pygments/console.py +13 -13
- data/vendor/pygments-main/pygments/filter.py +7 -7
- data/vendor/pygments-main/pygments/filters/__init__.py +24 -32
- data/vendor/pygments-main/pygments/formatter.py +5 -5
- data/vendor/pygments-main/pygments/formatters/__init__.py +92 -44
- data/vendor/pygments-main/pygments/formatters/_mapping.py +51 -69
- data/vendor/pygments-main/pygments/formatters/bbcode.py +1 -1
- data/vendor/pygments-main/pygments/formatters/html.py +63 -51
- data/vendor/pygments-main/pygments/formatters/img.py +25 -22
- data/vendor/pygments-main/pygments/formatters/irc.py +182 -0
- data/vendor/pygments-main/pygments/formatters/latex.py +34 -22
- data/vendor/pygments-main/pygments/formatters/other.py +5 -7
- data/vendor/pygments-main/pygments/formatters/rtf.py +28 -31
- data/vendor/pygments-main/pygments/formatters/svg.py +1 -2
- data/vendor/pygments-main/pygments/formatters/terminal.py +29 -45
- data/vendor/pygments-main/pygments/formatters/terminal256.py +118 -31
- data/vendor/pygments-main/pygments/lexer.py +120 -34
- data/vendor/pygments-main/pygments/lexers/__init__.py +85 -53
- data/vendor/pygments-main/pygments/lexers/{_asybuiltins.py → _asy_builtins.py} +7 -7
- data/vendor/pygments-main/pygments/lexers/{_clbuiltins.py → _cl_builtins.py} +17 -17
- data/vendor/pygments-main/pygments/lexers/_cocoa_builtins.py +72 -0
- data/vendor/pygments-main/pygments/lexers/_csound_builtins.py +1346 -0
- data/vendor/pygments-main/pygments/lexers/{_lassobuiltins.py → _lasso_builtins.py} +4699 -4561
- data/vendor/pygments-main/pygments/lexers/{_luabuiltins.py → _lua_builtins.py} +91 -51
- data/vendor/pygments-main/pygments/lexers/_mapping.py +342 -242
- data/vendor/pygments-main/pygments/lexers/_mql_builtins.py +1172 -0
- data/vendor/pygments-main/pygments/lexers/_openedge_builtins.py +2547 -0
- data/vendor/pygments-main/pygments/lexers/{_phpbuiltins.py → _php_builtins.py} +350 -353
- data/vendor/pygments-main/pygments/lexers/_postgres_builtins.py +600 -212
- data/vendor/pygments-main/pygments/lexers/_scilab_builtins.py +3084 -30
- data/vendor/pygments-main/pygments/lexers/_sourcemod_builtins.py +1163 -0
- data/vendor/pygments-main/pygments/lexers/_stan_builtins.py +91 -13
- data/vendor/pygments-main/pygments/lexers/_stata_builtins.py +419 -0
- data/vendor/pygments-main/pygments/lexers/_tsql_builtins.py +1004 -0
- data/vendor/pygments-main/pygments/lexers/_vim_builtins.py +1939 -0
- data/vendor/pygments-main/pygments/lexers/actionscript.py +240 -0
- data/vendor/pygments-main/pygments/lexers/agile.py +14 -2542
- data/vendor/pygments-main/pygments/lexers/algebra.py +221 -0
- data/vendor/pygments-main/pygments/lexers/ambient.py +76 -0
- data/vendor/pygments-main/pygments/lexers/ampl.py +87 -0
- data/vendor/pygments-main/pygments/lexers/apl.py +101 -0
- data/vendor/pygments-main/pygments/lexers/archetype.py +318 -0
- data/vendor/pygments-main/pygments/lexers/asm.py +276 -81
- data/vendor/pygments-main/pygments/lexers/automation.py +374 -0
- data/vendor/pygments-main/pygments/lexers/basic.py +500 -0
- data/vendor/pygments-main/pygments/lexers/bibtex.py +156 -0
- data/vendor/pygments-main/pygments/lexers/business.py +594 -0
- data/vendor/pygments-main/pygments/lexers/c_cpp.py +252 -0
- data/vendor/pygments-main/pygments/lexers/c_like.py +541 -0
- data/vendor/pygments-main/pygments/lexers/capnproto.py +79 -0
- data/vendor/pygments-main/pygments/lexers/chapel.py +101 -0
- data/vendor/pygments-main/pygments/lexers/clean.py +288 -0
- data/vendor/pygments-main/pygments/lexers/compiled.py +24 -5182
- data/vendor/pygments-main/pygments/lexers/configs.py +833 -0
- data/vendor/pygments-main/pygments/lexers/console.py +114 -0
- data/vendor/pygments-main/pygments/lexers/crystal.py +384 -0
- data/vendor/pygments-main/pygments/lexers/csound.py +366 -0
- data/vendor/pygments-main/pygments/lexers/css.py +689 -0
- data/vendor/pygments-main/pygments/lexers/d.py +251 -0
- data/vendor/pygments-main/pygments/lexers/dalvik.py +6 -6
- data/vendor/pygments-main/pygments/lexers/data.py +555 -0
- data/vendor/pygments-main/pygments/lexers/diff.py +165 -0
- data/vendor/pygments-main/pygments/lexers/dotnet.py +96 -88
- data/vendor/pygments-main/pygments/lexers/dsls.py +878 -0
- data/vendor/pygments-main/pygments/lexers/dylan.py +289 -0
- data/vendor/pygments-main/pygments/lexers/ecl.py +125 -0
- data/vendor/pygments-main/pygments/lexers/eiffel.py +65 -0
- data/vendor/pygments-main/pygments/lexers/elm.py +121 -0
- data/vendor/pygments-main/pygments/lexers/erlang.py +533 -0
- data/vendor/pygments-main/pygments/lexers/esoteric.py +275 -0
- data/vendor/pygments-main/pygments/lexers/ezhil.py +68 -0
- data/vendor/pygments-main/pygments/lexers/factor.py +344 -0
- data/vendor/pygments-main/pygments/lexers/fantom.py +250 -0
- data/vendor/pygments-main/pygments/lexers/felix.py +273 -0
- data/vendor/pygments-main/pygments/lexers/forth.py +177 -0
- data/vendor/pygments-main/pygments/lexers/fortran.py +205 -0
- data/vendor/pygments-main/pygments/lexers/foxpro.py +1 -1
- data/vendor/pygments-main/pygments/lexers/functional.py +11 -3661
- data/vendor/pygments-main/pygments/lexers/go.py +101 -0
- data/vendor/pygments-main/pygments/lexers/grammar_notation.py +213 -0
- data/vendor/pygments-main/pygments/lexers/graph.py +7 -8
- data/vendor/pygments-main/pygments/lexers/graphics.py +553 -0
- data/vendor/pygments-main/pygments/lexers/haskell.py +840 -0
- data/vendor/pygments-main/pygments/lexers/haxe.py +936 -0
- data/vendor/pygments-main/pygments/lexers/hdl.py +172 -145
- data/vendor/pygments-main/pygments/lexers/hexdump.py +97 -0
- data/vendor/pygments-main/pygments/lexers/html.py +602 -0
- data/vendor/pygments-main/pygments/lexers/idl.py +270 -0
- data/vendor/pygments-main/pygments/lexers/igor.py +288 -0
- data/vendor/pygments-main/pygments/lexers/inferno.py +3 -3
- data/vendor/pygments-main/pygments/lexers/installers.py +322 -0
- data/vendor/pygments-main/pygments/lexers/int_fiction.py +1343 -0
- data/vendor/pygments-main/pygments/lexers/iolang.py +63 -0
- data/vendor/pygments-main/pygments/lexers/j.py +146 -0
- data/vendor/pygments-main/pygments/lexers/javascript.py +1506 -0
- data/vendor/pygments-main/pygments/lexers/julia.py +333 -0
- data/vendor/pygments-main/pygments/lexers/jvm.py +232 -186
- data/vendor/pygments-main/pygments/lexers/lisp.py +2621 -0
- data/vendor/pygments-main/pygments/lexers/make.py +202 -0
- data/vendor/pygments-main/pygments/lexers/markup.py +595 -0
- data/vendor/pygments-main/pygments/lexers/math.py +11 -2276
- data/vendor/pygments-main/pygments/lexers/matlab.py +663 -0
- data/vendor/pygments-main/pygments/lexers/ml.py +769 -0
- data/vendor/pygments-main/pygments/lexers/modeling.py +358 -0
- data/vendor/pygments-main/pygments/lexers/modula2.py +1561 -0
- data/vendor/pygments-main/pygments/lexers/monte.py +203 -0
- data/vendor/pygments-main/pygments/lexers/ncl.py +1053 -0
- data/vendor/pygments-main/pygments/lexers/nimrod.py +159 -0
- data/vendor/pygments-main/pygments/lexers/nit.py +64 -0
- data/vendor/pygments-main/pygments/lexers/nix.py +136 -0
- data/vendor/pygments-main/pygments/lexers/oberon.py +105 -0
- data/vendor/pygments-main/pygments/lexers/objective.py +504 -0
- data/vendor/pygments-main/pygments/lexers/ooc.py +85 -0
- data/vendor/pygments-main/pygments/lexers/other.py +30 -4481
- data/vendor/pygments-main/pygments/lexers/parasail.py +79 -0
- data/vendor/pygments-main/pygments/lexers/parsers.py +171 -114
- data/vendor/pygments-main/pygments/lexers/pascal.py +644 -0
- data/vendor/pygments-main/pygments/lexers/pawn.py +199 -0
- data/vendor/pygments-main/pygments/lexers/perl.py +616 -0
- data/vendor/pygments-main/pygments/lexers/php.py +267 -0
- data/vendor/pygments-main/pygments/lexers/praat.py +294 -0
- data/vendor/pygments-main/pygments/lexers/prolog.py +306 -0
- data/vendor/pygments-main/pygments/lexers/python.py +938 -0
- data/vendor/pygments-main/pygments/lexers/qvt.py +152 -0
- data/vendor/pygments-main/pygments/lexers/r.py +453 -0
- data/vendor/pygments-main/pygments/lexers/rdf.py +195 -24
- data/vendor/pygments-main/pygments/lexers/rebol.py +431 -0
- data/vendor/pygments-main/pygments/lexers/resource.py +85 -0
- data/vendor/pygments-main/pygments/lexers/rnc.py +67 -0
- data/vendor/pygments-main/pygments/lexers/roboconf.py +82 -0
- data/vendor/pygments-main/pygments/lexers/{_robotframeworklexer.py → robotframework.py} +20 -18
- data/vendor/pygments-main/pygments/lexers/ruby.py +519 -0
- data/vendor/pygments-main/pygments/lexers/rust.py +209 -0
- data/vendor/pygments-main/pygments/lexers/sas.py +228 -0
- data/vendor/pygments-main/pygments/lexers/scripting.py +1222 -0
- data/vendor/pygments-main/pygments/lexers/shell.py +478 -115
- data/vendor/pygments-main/pygments/lexers/smalltalk.py +195 -0
- data/vendor/pygments-main/pygments/lexers/smv.py +75 -0
- data/vendor/pygments-main/pygments/lexers/snobol.py +83 -0
- data/vendor/pygments-main/pygments/lexers/special.py +6 -2
- data/vendor/pygments-main/pygments/lexers/sql.py +209 -120
- data/vendor/pygments-main/pygments/lexers/stata.py +106 -0
- data/vendor/pygments-main/pygments/lexers/supercollider.py +90 -0
- data/vendor/pygments-main/pygments/lexers/tcl.py +145 -0
- data/vendor/pygments-main/pygments/lexers/templates.py +282 -90
- data/vendor/pygments-main/pygments/lexers/testing.py +207 -0
- data/vendor/pygments-main/pygments/lexers/text.py +15 -2045
- data/vendor/pygments-main/pygments/lexers/textedit.py +169 -0
- data/vendor/pygments-main/pygments/lexers/textfmts.py +297 -0
- data/vendor/pygments-main/pygments/lexers/theorem.py +458 -0
- data/vendor/pygments-main/pygments/lexers/trafficscript.py +54 -0
- data/vendor/pygments-main/pygments/lexers/typoscript.py +225 -0
- data/vendor/pygments-main/pygments/lexers/urbi.py +133 -0
- data/vendor/pygments-main/pygments/lexers/varnish.py +190 -0
- data/vendor/pygments-main/pygments/lexers/verification.py +111 -0
- data/vendor/pygments-main/pygments/lexers/web.py +13 -4499
- data/vendor/pygments-main/pygments/lexers/webmisc.py +979 -0
- data/vendor/pygments-main/pygments/lexers/whiley.py +117 -0
- data/vendor/pygments-main/pygments/lexers/x10.py +69 -0
- data/vendor/pygments-main/pygments/modeline.py +5 -2
- data/vendor/pygments-main/pygments/plugin.py +1 -1
- data/vendor/pygments-main/pygments/regexopt.py +92 -0
- data/vendor/pygments-main/pygments/scanner.py +3 -2
- data/vendor/pygments-main/pygments/sphinxext.py +11 -6
- data/vendor/pygments-main/pygments/style.py +41 -4
- data/vendor/pygments-main/pygments/styles/__init__.py +5 -1
- data/vendor/pygments-main/pygments/styles/algol.py +63 -0
- data/vendor/pygments-main/pygments/styles/algol_nu.py +63 -0
- data/vendor/pygments-main/pygments/styles/arduino.py +98 -0
- data/vendor/pygments-main/pygments/styles/autumn.py +1 -1
- data/vendor/pygments-main/pygments/styles/borland.py +1 -1
- data/vendor/pygments-main/pygments/styles/bw.py +1 -1
- data/vendor/pygments-main/pygments/styles/colorful.py +1 -1
- data/vendor/pygments-main/pygments/styles/default.py +1 -1
- data/vendor/pygments-main/pygments/styles/emacs.py +1 -1
- data/vendor/pygments-main/pygments/styles/friendly.py +1 -1
- data/vendor/pygments-main/pygments/styles/fruity.py +1 -1
- data/vendor/pygments-main/pygments/styles/igor.py +1 -1
- data/vendor/pygments-main/pygments/styles/lovelace.py +97 -0
- data/vendor/pygments-main/pygments/styles/manni.py +1 -1
- data/vendor/pygments-main/pygments/styles/monokai.py +1 -1
- data/vendor/pygments-main/pygments/styles/murphy.py +1 -1
- data/vendor/pygments-main/pygments/styles/native.py +1 -1
- data/vendor/pygments-main/pygments/styles/paraiso_dark.py +1 -1
- data/vendor/pygments-main/pygments/styles/paraiso_light.py +1 -1
- data/vendor/pygments-main/pygments/styles/pastie.py +1 -1
- data/vendor/pygments-main/pygments/styles/perldoc.py +2 -2
- data/vendor/pygments-main/pygments/styles/rrt.py +1 -1
- data/vendor/pygments-main/pygments/styles/sas.py +41 -0
- data/vendor/pygments-main/pygments/styles/stata.py +37 -0
- data/vendor/pygments-main/pygments/styles/tango.py +1 -1
- data/vendor/pygments-main/pygments/styles/trac.py +1 -1
- data/vendor/pygments-main/pygments/styles/vim.py +1 -1
- data/vendor/pygments-main/pygments/styles/vs.py +1 -1
- data/vendor/pygments-main/pygments/styles/xcode.py +1 -1
- data/vendor/pygments-main/pygments/token.py +31 -16
- data/vendor/pygments-main/pygments/unistring.py +141 -65
- data/vendor/pygments-main/pygments/util.py +129 -33
- data/vendor/pygments-main/requirements.txt +5 -0
- data/vendor/pygments-main/scripts/check_sources.py +25 -40
- data/vendor/pygments-main/scripts/debug_lexer.py +246 -0
- data/vendor/pygments-main/scripts/find_error.py +1 -0
- data/vendor/pygments-main/scripts/get_vimkw.py +35 -4
- data/vendor/pygments-main/setup.cfg +3 -0
- data/vendor/pygments-main/setup.py +17 -30
- data/vendor/pygments-main/tox.ini +7 -0
- metadata +159 -387
- data/vendor/pygments-main/ez_setup.py +0 -382
- data/vendor/pygments-main/pygments/lexers/_cocoabuiltins.py +0 -73
- data/vendor/pygments-main/pygments/lexers/_openedgebuiltins.py +0 -562
- data/vendor/pygments-main/pygments/lexers/_sourcemodbuiltins.py +0 -1077
- data/vendor/pygments-main/pygments/lexers/_vimbuiltins.py +0 -13
- data/vendor/pygments-main/pygments/lexers/qbasic.py +0 -157
- data/vendor/pygments-main/scripts/find_codetags.py +0 -213
- data/vendor/pygments-main/scripts/find_error.py +0 -173
- data/vendor/pygments-main/tests/dtds/HTML4-f.dtd +0 -37
- data/vendor/pygments-main/tests/dtds/HTML4-s.dtd +0 -869
- data/vendor/pygments-main/tests/dtds/HTML4.dcl +0 -88
- data/vendor/pygments-main/tests/dtds/HTML4.dtd +0 -1092
- data/vendor/pygments-main/tests/dtds/HTML4.soc +0 -9
- data/vendor/pygments-main/tests/dtds/HTMLlat1.ent +0 -195
- data/vendor/pygments-main/tests/dtds/HTMLspec.ent +0 -77
- data/vendor/pygments-main/tests/dtds/HTMLsym.ent +0 -241
- data/vendor/pygments-main/tests/examplefiles/99_bottles_of_beer.chpl +0 -118
- data/vendor/pygments-main/tests/examplefiles/AcidStateAdvanced.hs +0 -209
- data/vendor/pygments-main/tests/examplefiles/AlternatingGroup.mu +0 -102
- data/vendor/pygments-main/tests/examplefiles/BOM.js +0 -1
- data/vendor/pygments-main/tests/examplefiles/CPDictionary.j +0 -611
- data/vendor/pygments-main/tests/examplefiles/Config.in.cache +0 -1973
- data/vendor/pygments-main/tests/examplefiles/Constants.mo +0 -158
- data/vendor/pygments-main/tests/examplefiles/DancingSudoku.lhs +0 -411
- data/vendor/pygments-main/tests/examplefiles/Deflate.fs +0 -578
- data/vendor/pygments-main/tests/examplefiles/Error.pmod +0 -38
- data/vendor/pygments-main/tests/examplefiles/Errors.scala +0 -18
- data/vendor/pygments-main/tests/examplefiles/FakeFile.pike +0 -360
- data/vendor/pygments-main/tests/examplefiles/Get-CommandDefinitionHtml.ps1 +0 -66
- data/vendor/pygments-main/tests/examplefiles/IPDispatchC.nc +0 -104
- data/vendor/pygments-main/tests/examplefiles/IPDispatchP.nc +0 -671
- data/vendor/pygments-main/tests/examplefiles/Intro.java +0 -1660
- data/vendor/pygments-main/tests/examplefiles/Makefile +0 -1131
- data/vendor/pygments-main/tests/examplefiles/Object.st +0 -4394
- data/vendor/pygments-main/tests/examplefiles/OrderedMap.hx +0 -584
- data/vendor/pygments-main/tests/examplefiles/RoleQ.pm6 +0 -23
- data/vendor/pygments-main/tests/examplefiles/SmallCheck.hs +0 -378
- data/vendor/pygments-main/tests/examplefiles/Sorting.mod +0 -470
- data/vendor/pygments-main/tests/examplefiles/Sudoku.lhs +0 -382
- data/vendor/pygments-main/tests/examplefiles/addressbook.proto +0 -30
- data/vendor/pygments-main/tests/examplefiles/antlr_ANTLRv3.g +0 -608
- data/vendor/pygments-main/tests/examplefiles/antlr_throws +0 -1
- data/vendor/pygments-main/tests/examplefiles/apache2.conf +0 -393
- data/vendor/pygments-main/tests/examplefiles/as3_test.as +0 -143
- data/vendor/pygments-main/tests/examplefiles/as3_test2.as +0 -46
- data/vendor/pygments-main/tests/examplefiles/as3_test3.as +0 -3
- data/vendor/pygments-main/tests/examplefiles/aspx-cs_example +0 -27
- data/vendor/pygments-main/tests/examplefiles/autoit_submit.au3 +0 -25
- data/vendor/pygments-main/tests/examplefiles/badcase.java +0 -2
- data/vendor/pygments-main/tests/examplefiles/batchfile.bat +0 -49
- data/vendor/pygments-main/tests/examplefiles/bigtest.nsi +0 -308
- data/vendor/pygments-main/tests/examplefiles/boot-9.scm +0 -1557
- data/vendor/pygments-main/tests/examplefiles/ca65_example +0 -284
- data/vendor/pygments-main/tests/examplefiles/cbmbas_example +0 -9
- data/vendor/pygments-main/tests/examplefiles/cells.ps +0 -515
- data/vendor/pygments-main/tests/examplefiles/ceval.c +0 -2604
- data/vendor/pygments-main/tests/examplefiles/cheetah_example.html +0 -13
- data/vendor/pygments-main/tests/examplefiles/classes.dylan +0 -125
- data/vendor/pygments-main/tests/examplefiles/clojure-weird-keywords.clj +0 -5
- data/vendor/pygments-main/tests/examplefiles/condensed_ruby.rb +0 -10
- data/vendor/pygments-main/tests/examplefiles/coq_RelationClasses +0 -447
- data/vendor/pygments-main/tests/examplefiles/core.cljs +0 -52
- data/vendor/pygments-main/tests/examplefiles/database.pytb +0 -20
- data/vendor/pygments-main/tests/examplefiles/de.MoinMoin.po +0 -2461
- data/vendor/pygments-main/tests/examplefiles/demo.ahk +0 -181
- data/vendor/pygments-main/tests/examplefiles/demo.cfm +0 -50
- data/vendor/pygments-main/tests/examplefiles/demo.hbs +0 -12
- data/vendor/pygments-main/tests/examplefiles/django_sample.html+django +0 -68
- data/vendor/pygments-main/tests/examplefiles/dwarf.cw +0 -17
- data/vendor/pygments-main/tests/examplefiles/ember.handlebars +0 -33
- data/vendor/pygments-main/tests/examplefiles/erl_session +0 -10
- data/vendor/pygments-main/tests/examplefiles/escape_semicolon.clj +0 -1
- data/vendor/pygments-main/tests/examplefiles/evil_regex.js +0 -48
- data/vendor/pygments-main/tests/examplefiles/example.Rd +0 -78
- data/vendor/pygments-main/tests/examplefiles/example.als +0 -217
- data/vendor/pygments-main/tests/examplefiles/example.bug +0 -54
- data/vendor/pygments-main/tests/examplefiles/example.c +0 -2080
- data/vendor/pygments-main/tests/examplefiles/example.ceylon +0 -52
- data/vendor/pygments-main/tests/examplefiles/example.chai +0 -6
- data/vendor/pygments-main/tests/examplefiles/example.clay +0 -33
- data/vendor/pygments-main/tests/examplefiles/example.cls +0 -15
- data/vendor/pygments-main/tests/examplefiles/example.cob +0 -3556
- data/vendor/pygments-main/tests/examplefiles/example.coffee +0 -27
- data/vendor/pygments-main/tests/examplefiles/example.cpp +0 -2363
- data/vendor/pygments-main/tests/examplefiles/example.e +0 -124
- data/vendor/pygments-main/tests/examplefiles/example.f90 +0 -8
- data/vendor/pygments-main/tests/examplefiles/example.feature +0 -16
- data/vendor/pygments-main/tests/examplefiles/example.gd +0 -23
- data/vendor/pygments-main/tests/examplefiles/example.gi +0 -64
- data/vendor/pygments-main/tests/examplefiles/example.groovy +0 -2
- data/vendor/pygments-main/tests/examplefiles/example.gs +0 -106
- data/vendor/pygments-main/tests/examplefiles/example.gst +0 -7
- data/vendor/pygments-main/tests/examplefiles/example.hs +0 -27
- data/vendor/pygments-main/tests/examplefiles/example.hx +0 -185
- data/vendor/pygments-main/tests/examplefiles/example.i6t +0 -32
- data/vendor/pygments-main/tests/examplefiles/example.i7x +0 -45
- data/vendor/pygments-main/tests/examplefiles/example.inf +0 -374
- data/vendor/pygments-main/tests/examplefiles/example.j +0 -564
- data/vendor/pygments-main/tests/examplefiles/example.jag +0 -48
- data/vendor/pygments-main/tests/examplefiles/example.java +0 -16
- data/vendor/pygments-main/tests/examplefiles/example.kal +0 -75
- data/vendor/pygments-main/tests/examplefiles/example.kt +0 -47
- data/vendor/pygments-main/tests/examplefiles/example.lagda +0 -19
- data/vendor/pygments-main/tests/examplefiles/example.liquid +0 -42
- data/vendor/pygments-main/tests/examplefiles/example.lua +0 -250
- data/vendor/pygments-main/tests/examplefiles/example.ma +0 -8
- data/vendor/pygments-main/tests/examplefiles/example.monkey +0 -152
- data/vendor/pygments-main/tests/examplefiles/example.moo +0 -26
- data/vendor/pygments-main/tests/examplefiles/example.moon +0 -629
- data/vendor/pygments-main/tests/examplefiles/example.mq4 +0 -187
- data/vendor/pygments-main/tests/examplefiles/example.mqh +0 -123
- data/vendor/pygments-main/tests/examplefiles/example.msc +0 -43
- data/vendor/pygments-main/tests/examplefiles/example.ni +0 -57
- data/vendor/pygments-main/tests/examplefiles/example.nim +0 -1010
- data/vendor/pygments-main/tests/examplefiles/example.nix +0 -80
- data/vendor/pygments-main/tests/examplefiles/example.ns2 +0 -69
- data/vendor/pygments-main/tests/examplefiles/example.pas +0 -2708
- data/vendor/pygments-main/tests/examplefiles/example.pp +0 -8
- data/vendor/pygments-main/tests/examplefiles/example.prg +0 -161
- data/vendor/pygments-main/tests/examplefiles/example.rb +0 -1852
- data/vendor/pygments-main/tests/examplefiles/example.red +0 -257
- data/vendor/pygments-main/tests/examplefiles/example.reds +0 -150
- data/vendor/pygments-main/tests/examplefiles/example.reg +0 -19
- data/vendor/pygments-main/tests/examplefiles/example.rexx +0 -50
- data/vendor/pygments-main/tests/examplefiles/example.rhtml +0 -561
- data/vendor/pygments-main/tests/examplefiles/example.rkt +0 -743
- data/vendor/pygments-main/tests/examplefiles/example.rpf +0 -4
- data/vendor/pygments-main/tests/examplefiles/example.sh +0 -22
- data/vendor/pygments-main/tests/examplefiles/example.sh-session +0 -19
- data/vendor/pygments-main/tests/examplefiles/example.shell-session +0 -45
- data/vendor/pygments-main/tests/examplefiles/example.slim +0 -31
- data/vendor/pygments-main/tests/examplefiles/example.sls +0 -51
- data/vendor/pygments-main/tests/examplefiles/example.sml +0 -156
- data/vendor/pygments-main/tests/examplefiles/example.snobol +0 -15
- data/vendor/pygments-main/tests/examplefiles/example.stan +0 -110
- data/vendor/pygments-main/tests/examplefiles/example.tea +0 -34
- data/vendor/pygments-main/tests/examplefiles/example.todotxt +0 -9
- data/vendor/pygments-main/tests/examplefiles/example.ts +0 -28
- data/vendor/pygments-main/tests/examplefiles/example.u +0 -548
- data/vendor/pygments-main/tests/examplefiles/example.weechatlog +0 -9
- data/vendor/pygments-main/tests/examplefiles/example.xhtml +0 -376
- data/vendor/pygments-main/tests/examplefiles/example.xtend +0 -34
- data/vendor/pygments-main/tests/examplefiles/example.yaml +0 -302
- data/vendor/pygments-main/tests/examplefiles/example2.aspx +0 -29
- data/vendor/pygments-main/tests/examplefiles/example2.msc +0 -79
- data/vendor/pygments-main/tests/examplefiles/exampleScript.cfc +0 -241
- data/vendor/pygments-main/tests/examplefiles/exampleTag.cfc +0 -18
- data/vendor/pygments-main/tests/examplefiles/example_elixir.ex +0 -205
- data/vendor/pygments-main/tests/examplefiles/example_file.fy +0 -128
- data/vendor/pygments-main/tests/examplefiles/firefox.mak +0 -586
- data/vendor/pygments-main/tests/examplefiles/flipflop.sv +0 -19
- data/vendor/pygments-main/tests/examplefiles/foo.sce +0 -6
- data/vendor/pygments-main/tests/examplefiles/format.ml +0 -1213
- data/vendor/pygments-main/tests/examplefiles/fucked_up.rb +0 -77
- data/vendor/pygments-main/tests/examplefiles/function.mu +0 -1
- data/vendor/pygments-main/tests/examplefiles/functional.rst +0 -1472
- data/vendor/pygments-main/tests/examplefiles/garcia-wachs.kk +0 -133
- data/vendor/pygments-main/tests/examplefiles/genclass.clj +0 -510
- data/vendor/pygments-main/tests/examplefiles/genshi_example.xml+genshi +0 -193
- data/vendor/pygments-main/tests/examplefiles/genshitext_example.genshitext +0 -33
- data/vendor/pygments-main/tests/examplefiles/glsl.frag +0 -7
- data/vendor/pygments-main/tests/examplefiles/glsl.vert +0 -13
- data/vendor/pygments-main/tests/examplefiles/grammar-test.p6 +0 -22
- data/vendor/pygments-main/tests/examplefiles/hash_syntax.rb +0 -5
- data/vendor/pygments-main/tests/examplefiles/hello.at +0 -6
- data/vendor/pygments-main/tests/examplefiles/hello.golo +0 -5
- data/vendor/pygments-main/tests/examplefiles/hello.lsl +0 -12
- data/vendor/pygments-main/tests/examplefiles/hello.smali +0 -40
- data/vendor/pygments-main/tests/examplefiles/hello.sp +0 -9
- data/vendor/pygments-main/tests/examplefiles/html+php_faulty.php +0 -1
- data/vendor/pygments-main/tests/examplefiles/http_request_example +0 -15
- data/vendor/pygments-main/tests/examplefiles/http_response_example +0 -29
- data/vendor/pygments-main/tests/examplefiles/hybris_File.hy +0 -174
- data/vendor/pygments-main/tests/examplefiles/idl_sample.pro +0 -73
- data/vendor/pygments-main/tests/examplefiles/iex_example +0 -23
- data/vendor/pygments-main/tests/examplefiles/inet_pton6.dg +0 -71
- data/vendor/pygments-main/tests/examplefiles/intro.ik +0 -24
- data/vendor/pygments-main/tests/examplefiles/ints.php +0 -10
- data/vendor/pygments-main/tests/examplefiles/intsyn.fun +0 -675
- data/vendor/pygments-main/tests/examplefiles/intsyn.sig +0 -286
- data/vendor/pygments-main/tests/examplefiles/irb_heredoc +0 -8
- data/vendor/pygments-main/tests/examplefiles/irc.lsp +0 -214
- data/vendor/pygments-main/tests/examplefiles/java.properties +0 -16
- data/vendor/pygments-main/tests/examplefiles/jbst_example1.jbst +0 -28
- data/vendor/pygments-main/tests/examplefiles/jbst_example2.jbst +0 -45
- data/vendor/pygments-main/tests/examplefiles/jinjadesignerdoc.rst +0 -713
- data/vendor/pygments-main/tests/examplefiles/json.lasso +0 -301
- data/vendor/pygments-main/tests/examplefiles/json.lasso9 +0 -213
- data/vendor/pygments-main/tests/examplefiles/language.hy +0 -165
- data/vendor/pygments-main/tests/examplefiles/lighttpd_config.conf +0 -13
- data/vendor/pygments-main/tests/examplefiles/limbo.b +0 -456
- data/vendor/pygments-main/tests/examplefiles/linecontinuation.py +0 -47
- data/vendor/pygments-main/tests/examplefiles/livescript-demo.ls +0 -43
- data/vendor/pygments-main/tests/examplefiles/logos_example.xm +0 -28
- data/vendor/pygments-main/tests/examplefiles/ltmain.sh +0 -2849
- data/vendor/pygments-main/tests/examplefiles/main.cmake +0 -44
- data/vendor/pygments-main/tests/examplefiles/markdown.lsp +0 -679
- data/vendor/pygments-main/tests/examplefiles/matlab_noreturn +0 -3
- data/vendor/pygments-main/tests/examplefiles/matlab_sample +0 -30
- data/vendor/pygments-main/tests/examplefiles/matlabsession_sample.txt +0 -37
- data/vendor/pygments-main/tests/examplefiles/metagrammar.treetop +0 -455
- data/vendor/pygments-main/tests/examplefiles/minehunt.qml +0 -112
- data/vendor/pygments-main/tests/examplefiles/minimal.ns2 +0 -4
- data/vendor/pygments-main/tests/examplefiles/moin_SyntaxReference.txt +0 -340
- data/vendor/pygments-main/tests/examplefiles/multiline_regexes.rb +0 -38
- data/vendor/pygments-main/tests/examplefiles/nanomsg.intr +0 -95
- data/vendor/pygments-main/tests/examplefiles/nasm_aoutso.asm +0 -96
- data/vendor/pygments-main/tests/examplefiles/nasm_objexe.asm +0 -30
- data/vendor/pygments-main/tests/examplefiles/nemerle_sample.n +0 -87
- data/vendor/pygments-main/tests/examplefiles/nginx_nginx.conf +0 -118
- data/vendor/pygments-main/tests/examplefiles/numbers.c +0 -12
- data/vendor/pygments-main/tests/examplefiles/objc_example.m +0 -179
- data/vendor/pygments-main/tests/examplefiles/openedge_example +0 -34
- data/vendor/pygments-main/tests/examplefiles/pawn_example +0 -25
- data/vendor/pygments-main/tests/examplefiles/perl_misc +0 -62
- data/vendor/pygments-main/tests/examplefiles/perl_perl5db +0 -998
- data/vendor/pygments-main/tests/examplefiles/perl_regex-delims +0 -120
- data/vendor/pygments-main/tests/examplefiles/perlfunc.1 +0 -856
- data/vendor/pygments-main/tests/examplefiles/phpMyAdmin.spec +0 -163
- data/vendor/pygments-main/tests/examplefiles/phpcomplete.vim +0 -567
- data/vendor/pygments-main/tests/examplefiles/pleac.in.rb +0 -1223
- data/vendor/pygments-main/tests/examplefiles/postgresql_test.txt +0 -47
- data/vendor/pygments-main/tests/examplefiles/pppoe.applescript +0 -10
- data/vendor/pygments-main/tests/examplefiles/psql_session.txt +0 -122
- data/vendor/pygments-main/tests/examplefiles/py3_test.txt +0 -2
- data/vendor/pygments-main/tests/examplefiles/py3tb_test.py3tb +0 -4
- data/vendor/pygments-main/tests/examplefiles/pycon_test.pycon +0 -14
- data/vendor/pygments-main/tests/examplefiles/pytb_test2.pytb +0 -2
- data/vendor/pygments-main/tests/examplefiles/pytb_test3.pytb +0 -4
- data/vendor/pygments-main/tests/examplefiles/python25-bsd.mak +0 -234
- data/vendor/pygments-main/tests/examplefiles/qbasic_example +0 -2
- data/vendor/pygments-main/tests/examplefiles/qsort.prolog +0 -13
- data/vendor/pygments-main/tests/examplefiles/r-console-transcript.Rout +0 -38
- data/vendor/pygments-main/tests/examplefiles/r6rs-comments.scm +0 -23
- data/vendor/pygments-main/tests/examplefiles/ragel-cpp_rlscan +0 -280
- data/vendor/pygments-main/tests/examplefiles/ragel-cpp_snippet +0 -2
- data/vendor/pygments-main/tests/examplefiles/regex.js +0 -22
- data/vendor/pygments-main/tests/examplefiles/reversi.lsp +0 -427
- data/vendor/pygments-main/tests/examplefiles/robotframework_test.txt +0 -39
- data/vendor/pygments-main/tests/examplefiles/rql-queries.rql +0 -34
- data/vendor/pygments-main/tests/examplefiles/ruby_func_def.rb +0 -11
- data/vendor/pygments-main/tests/examplefiles/rust_example.rs +0 -233
- data/vendor/pygments-main/tests/examplefiles/scilab.sci +0 -30
- data/vendor/pygments-main/tests/examplefiles/scope.cirru +0 -43
- data/vendor/pygments-main/tests/examplefiles/session.dylan-console +0 -9
- data/vendor/pygments-main/tests/examplefiles/sibling.prolog +0 -19
- data/vendor/pygments-main/tests/examplefiles/simple.md +0 -747
- data/vendor/pygments-main/tests/examplefiles/smarty_example.html +0 -209
- data/vendor/pygments-main/tests/examplefiles/source.lgt +0 -343
- data/vendor/pygments-main/tests/examplefiles/sources.list +0 -62
- data/vendor/pygments-main/tests/examplefiles/sparql.rq +0 -23
- data/vendor/pygments-main/tests/examplefiles/sphere.pov +0 -18
- data/vendor/pygments-main/tests/examplefiles/sqlite3.sqlite3-console +0 -27
- data/vendor/pygments-main/tests/examplefiles/squid.conf +0 -30
- data/vendor/pygments-main/tests/examplefiles/string.jl +0 -1031
- data/vendor/pygments-main/tests/examplefiles/string_delimiters.d +0 -21
- data/vendor/pygments-main/tests/examplefiles/stripheredoc.sh +0 -3
- data/vendor/pygments-main/tests/examplefiles/swig_java.swg +0 -1329
- data/vendor/pygments-main/tests/examplefiles/swig_std_vector.i +0 -225
- data/vendor/pygments-main/tests/examplefiles/test.R +0 -185
- data/vendor/pygments-main/tests/examplefiles/test.adb +0 -211
- data/vendor/pygments-main/tests/examplefiles/test.agda +0 -102
- data/vendor/pygments-main/tests/examplefiles/test.apl +0 -26
- data/vendor/pygments-main/tests/examplefiles/test.asy +0 -131
- data/vendor/pygments-main/tests/examplefiles/test.awk +0 -121
- data/vendor/pygments-main/tests/examplefiles/test.bb +0 -95
- data/vendor/pygments-main/tests/examplefiles/test.bmx +0 -145
- data/vendor/pygments-main/tests/examplefiles/test.boo +0 -39
- data/vendor/pygments-main/tests/examplefiles/test.bro +0 -250
- data/vendor/pygments-main/tests/examplefiles/test.cs +0 -374
- data/vendor/pygments-main/tests/examplefiles/test.css +0 -54
- data/vendor/pygments-main/tests/examplefiles/test.cu +0 -36
- data/vendor/pygments-main/tests/examplefiles/test.cyp +0 -123
- data/vendor/pygments-main/tests/examplefiles/test.d +0 -135
- data/vendor/pygments-main/tests/examplefiles/test.dart +0 -23
- data/vendor/pygments-main/tests/examplefiles/test.dtd +0 -89
- data/vendor/pygments-main/tests/examplefiles/test.ebnf +0 -31
- data/vendor/pygments-main/tests/examplefiles/test.ec +0 -605
- data/vendor/pygments-main/tests/examplefiles/test.ecl +0 -58
- data/vendor/pygments-main/tests/examplefiles/test.eh +0 -315
- data/vendor/pygments-main/tests/examplefiles/test.erl +0 -169
- data/vendor/pygments-main/tests/examplefiles/test.evoque +0 -33
- data/vendor/pygments-main/tests/examplefiles/test.fan +0 -818
- data/vendor/pygments-main/tests/examplefiles/test.flx +0 -57
- data/vendor/pygments-main/tests/examplefiles/test.gdc +0 -13
- data/vendor/pygments-main/tests/examplefiles/test.groovy +0 -97
- data/vendor/pygments-main/tests/examplefiles/test.html +0 -339
- data/vendor/pygments-main/tests/examplefiles/test.idr +0 -93
- data/vendor/pygments-main/tests/examplefiles/test.ini +0 -10
- data/vendor/pygments-main/tests/examplefiles/test.java +0 -653
- data/vendor/pygments-main/tests/examplefiles/test.jsp +0 -24
- data/vendor/pygments-main/tests/examplefiles/test.maql +0 -45
- data/vendor/pygments-main/tests/examplefiles/test.mask +0 -41
- data/vendor/pygments-main/tests/examplefiles/test.mod +0 -374
- data/vendor/pygments-main/tests/examplefiles/test.moo +0 -51
- data/vendor/pygments-main/tests/examplefiles/test.myt +0 -166
- data/vendor/pygments-main/tests/examplefiles/test.nim +0 -93
- data/vendor/pygments-main/tests/examplefiles/test.opa +0 -10
- data/vendor/pygments-main/tests/examplefiles/test.p6 +0 -252
- data/vendor/pygments-main/tests/examplefiles/test.pan +0 -54
- data/vendor/pygments-main/tests/examplefiles/test.pas +0 -743
- data/vendor/pygments-main/tests/examplefiles/test.php +0 -507
- data/vendor/pygments-main/tests/examplefiles/test.pig +0 -148
- data/vendor/pygments-main/tests/examplefiles/test.plot +0 -333
- data/vendor/pygments-main/tests/examplefiles/test.ps1 +0 -108
- data/vendor/pygments-main/tests/examplefiles/test.pwn +0 -253
- data/vendor/pygments-main/tests/examplefiles/test.pypylog +0 -1839
- data/vendor/pygments-main/tests/examplefiles/test.r3 +0 -114
- data/vendor/pygments-main/tests/examplefiles/test.rb +0 -177
- data/vendor/pygments-main/tests/examplefiles/test.rhtml +0 -43
- data/vendor/pygments-main/tests/examplefiles/test.rsl +0 -111
- data/vendor/pygments-main/tests/examplefiles/test.scaml +0 -8
- data/vendor/pygments-main/tests/examplefiles/test.ssp +0 -12
- data/vendor/pygments-main/tests/examplefiles/test.swift +0 -65
- data/vendor/pygments-main/tests/examplefiles/test.tcsh +0 -830
- data/vendor/pygments-main/tests/examplefiles/test.vb +0 -407
- data/vendor/pygments-main/tests/examplefiles/test.vhdl +0 -161
- data/vendor/pygments-main/tests/examplefiles/test.xqy +0 -138
- data/vendor/pygments-main/tests/examplefiles/test.xsl +0 -23
- data/vendor/pygments-main/tests/examplefiles/test.zep +0 -33
- data/vendor/pygments-main/tests/examplefiles/test2.pypylog +0 -120
- data/vendor/pygments-main/tests/examplefiles/truncated.pytb +0 -15
- data/vendor/pygments-main/tests/examplefiles/type.lisp +0 -1218
- data/vendor/pygments-main/tests/examplefiles/underscore.coffee +0 -603
- data/vendor/pygments-main/tests/examplefiles/unicode.applescript +0 -5
- data/vendor/pygments-main/tests/examplefiles/unicode.go +0 -10
- data/vendor/pygments-main/tests/examplefiles/unicodedoc.py +0 -11
- data/vendor/pygments-main/tests/examplefiles/unix-io.lid +0 -37
- data/vendor/pygments-main/tests/examplefiles/vbnet_test.bas +0 -29
- data/vendor/pygments-main/tests/examplefiles/vctreestatus_hg +0 -4
- data/vendor/pygments-main/tests/examplefiles/vimrc +0 -21
- data/vendor/pygments-main/tests/examplefiles/webkit-transition.css +0 -3
- data/vendor/pygments-main/tests/examplefiles/while.pov +0 -13
- data/vendor/pygments-main/tests/examplefiles/wiki.factor +0 -384
- data/vendor/pygments-main/tests/examplefiles/xml_example +0 -1897
- data/vendor/pygments-main/tests/examplefiles/zmlrpc.f90 +0 -798
- data/vendor/pygments-main/tests/run.py +0 -44
- data/vendor/pygments-main/tests/string_asserts.py +0 -22
- data/vendor/pygments-main/tests/support.py +0 -15
- data/vendor/pygments-main/tests/support/tags +0 -36
- data/vendor/pygments-main/tests/test_basic_api.py +0 -309
- data/vendor/pygments-main/tests/test_cfm.py +0 -46
- data/vendor/pygments-main/tests/test_clexer.py +0 -236
- data/vendor/pygments-main/tests/test_cmdline.py +0 -106
- data/vendor/pygments-main/tests/test_examplefiles.py +0 -110
- data/vendor/pygments-main/tests/test_html_formatter.py +0 -180
- data/vendor/pygments-main/tests/test_latex_formatter.py +0 -57
- data/vendor/pygments-main/tests/test_lexers_other.py +0 -68
- data/vendor/pygments-main/tests/test_objectiveclexer.py +0 -81
- data/vendor/pygments-main/tests/test_perllexer.py +0 -137
- data/vendor/pygments-main/tests/test_qbasiclexer.py +0 -43
- data/vendor/pygments-main/tests/test_regexlexer.py +0 -54
- data/vendor/pygments-main/tests/test_rtf_formatter.py +0 -109
- data/vendor/pygments-main/tests/test_string_asserts.py +0 -39
- data/vendor/pygments-main/tests/test_token.py +0 -46
- data/vendor/pygments-main/tests/test_using_api.py +0 -40
- data/vendor/pygments-main/tests/test_util.py +0 -135
@@ -1,161 +0,0 @@
|
|
1
|
-
&& This is a concatenation of all VFP examples on Wikipedia.
|
2
|
-
&& Copyright 2013 Wikimedia, under the GFDL.
|
3
|
-
|
4
|
-
FOR i = 1 to 10
|
5
|
-
x = x + 6.5
|
6
|
-
ENDFOR
|
7
|
-
|
8
|
-
IF i = 25
|
9
|
-
i = i + 1
|
10
|
-
ELSE
|
11
|
-
i = i + 3
|
12
|
-
ENDIF
|
13
|
-
|
14
|
-
x = 1
|
15
|
-
DO WHILE x < 50
|
16
|
-
x = x + 1
|
17
|
-
ENDDO
|
18
|
-
|
19
|
-
x = 1
|
20
|
-
DO WHILE .T.
|
21
|
-
x = x + 1
|
22
|
-
IF x < 50
|
23
|
-
LOOP
|
24
|
-
ELSE
|
25
|
-
EXIT
|
26
|
-
ENDIF
|
27
|
-
ENDDO
|
28
|
-
|
29
|
-
nMonth = MONTH(DATE())
|
30
|
-
DO CASE
|
31
|
-
CASE nMonth <= 3
|
32
|
-
MESSAGEBOX("Q1")
|
33
|
-
|
34
|
-
CASE nMonth <= 6
|
35
|
-
MESSAGEBOX("Q2")
|
36
|
-
|
37
|
-
CASE nMonth <= 9
|
38
|
-
MESSAGEBOX("Q3")
|
39
|
-
|
40
|
-
OTHERWISE
|
41
|
-
MESSAGEBOX("Q4")
|
42
|
-
ENDCASE
|
43
|
-
|
44
|
-
FOR EACH oControl IN THISFORM.Controls
|
45
|
-
MESSAGEBOX(oControl.Name)
|
46
|
-
ENDFOR
|
47
|
-
|
48
|
-
f = Factorial(10)
|
49
|
-
|
50
|
-
FUNCTION Factorial(n)
|
51
|
-
LOCAL i,r
|
52
|
-
r = 1
|
53
|
-
FOR i = n TO 1 STEP -1
|
54
|
-
r = r * n
|
55
|
-
ENDFOR
|
56
|
-
RETURN r
|
57
|
-
ENDFUNC
|
58
|
-
|
59
|
-
loForm = CREATEOBJECT("HiForm")
|
60
|
-
loForm.Show(1)
|
61
|
-
|
62
|
-
DEFINE CLASS HiForm AS Form
|
63
|
-
AutoCenter = .T.
|
64
|
-
Caption = "Hello, World"
|
65
|
-
|
66
|
-
ADD OBJECT lblHi as Label WITH ;
|
67
|
-
Caption = "Hello, World!"
|
68
|
-
ENDDEFINE
|
69
|
-
|
70
|
-
loMine = CREATEOBJECT("MyClass")
|
71
|
-
? loMine.cProp1 && This will work. (Double-ampersand marks an end-of-line comment)
|
72
|
-
? loMine.cProp2 && Program Error: Property CPROP2 is not found.
|
73
|
-
|
74
|
-
? loMine.MyMethod1() && This will work.
|
75
|
-
? loMine.MyMethod2() && Program Error: Property MYMETHOD2 is not found.
|
76
|
-
|
77
|
-
DEFINE CLASS MyClass AS Custom
|
78
|
-
cProp1 = "My Property" && This is a public property
|
79
|
-
HIDDEN cProp2 && This is a private (hidden) property
|
80
|
-
dProp3 = {} && Another public property
|
81
|
-
|
82
|
-
PROCEDURE Init() && Class constructor
|
83
|
-
This.cProp2 = "This is a hidden property."
|
84
|
-
ENDPROC
|
85
|
-
|
86
|
-
PROCEDURE dProp3_Access && Property Getter
|
87
|
-
RETURN DATE()
|
88
|
-
ENDPROC
|
89
|
-
PROCEDURE dProp3_Assign(vNewVal) && Property Setter
|
90
|
-
IF VARTYPE(vNewVal) = "D"
|
91
|
-
THIS.dProp3 = vNewVal
|
92
|
-
ENDIF
|
93
|
-
ENDPROC
|
94
|
-
|
95
|
-
PROCEDURE MyMethod1()
|
96
|
-
* This is a public method, calling a hidden method that returns
|
97
|
-
* the value of a hidden property.
|
98
|
-
RETURN This.MyMethod2()
|
99
|
-
ENDPROC
|
100
|
-
|
101
|
-
HIDDEN PROCEDURE MyMethod2() && This is a private (hidden) method
|
102
|
-
RETURN This.cProp2
|
103
|
-
ENDPROC
|
104
|
-
ENDDEFINE
|
105
|
-
|
106
|
-
&& Create a table
|
107
|
-
CREATE TABLE randData (iData I)
|
108
|
-
|
109
|
-
&& Populate with random data using xBase and SQL DML commands
|
110
|
-
FOR i = 1 TO 50
|
111
|
-
APPEND BLANK
|
112
|
-
REPLACE iData WITH (RAND() * 100)
|
113
|
-
|
114
|
-
INSERT INTO randData (iData) VALUES (RAND() * 100)
|
115
|
-
ENDFOR
|
116
|
-
|
117
|
-
&& Place a structural index on the data
|
118
|
-
INDEX ON iData TAG iData
|
119
|
-
CLOSE ALL
|
120
|
-
|
121
|
-
&& Display ordered data using xBase-style commands
|
122
|
-
USE randData
|
123
|
-
SET ORDER TO iData
|
124
|
-
GO TOP
|
125
|
-
LIST NEXT 10 && First 10
|
126
|
-
GO BOTTOM
|
127
|
-
SKIP -10
|
128
|
-
LIST REST && Last 10
|
129
|
-
CLOSE ALL
|
130
|
-
|
131
|
-
&& Browse ordered data using SQL DML commands
|
132
|
-
SELECT * ;
|
133
|
-
FROM randData ;
|
134
|
-
ORDER BY iData DESCENDING
|
135
|
-
|
136
|
-
|
137
|
-
&& Connect to an ODBC data source
|
138
|
-
LOCAL nHnd
|
139
|
-
nHnd = SQLCONNECT ("ODBCDSN", "user", "pwd")
|
140
|
-
|
141
|
-
&& Execute a SQL command
|
142
|
-
LOCAL nResult
|
143
|
-
nResult = SQLEXEC (nHnd, "USE master")
|
144
|
-
IF nResult < 0
|
145
|
-
MESSAGEBOX ("MASTER database does not exist!")
|
146
|
-
RETURN
|
147
|
-
ENDIF
|
148
|
-
|
149
|
-
&& Retrieve data from the remote server and stores it in
|
150
|
-
&& a local data cursor
|
151
|
-
nResult = SQLEXEC (nHnd, "SELECT * FROM authors", "QAUTHORS")
|
152
|
-
|
153
|
-
&& Update a record in a remote table using parameters
|
154
|
-
PRIVATE cAuthorID, cAuthorName
|
155
|
-
cAuthorID = "1001"
|
156
|
-
cAuthorName = "New name"
|
157
|
-
nResult = SQLEXEC (nHnd, "UPDATE authors SET auth_name = ?cAuthorName WHERE auth_id = ?cAuthorID")
|
158
|
-
|
159
|
-
&& Close the connection
|
160
|
-
SQLDISCONNECT(nHnd)
|
161
|
-
|
@@ -1,1852 +0,0 @@
|
|
1
|
-
module CodeRay
|
2
|
-
module Scanners
|
3
|
-
|
4
|
-
class Ruby < Scanner
|
5
|
-
|
6
|
-
RESERVED_WORDS = [
|
7
|
-
'and', 'def', 'end', 'in', 'or', 'unless', 'begin',
|
8
|
-
'defined?', 'ensure', 'module', 'redo', 'super', 'until',
|
9
|
-
'BEGIN', 'break', 'do', 'next', 'rescue', 'then',
|
10
|
-
'when', 'END', 'case', 'else', 'for', 'retry',
|
11
|
-
'while', 'alias', 'class', 'elsif', 'if', 'not', 'return',
|
12
|
-
'undef', 'yield',
|
13
|
-
]
|
14
|
-
|
15
|
-
DEF_KEYWORDS = ['def']
|
16
|
-
MODULE_KEYWORDS = ['class', 'module']
|
17
|
-
DEF_NEW_STATE = WordList.new(:initial).
|
18
|
-
add(DEF_KEYWORDS, :def_expected).
|
19
|
-
add(MODULE_KEYWORDS, :module_expected)
|
20
|
-
|
21
|
-
WORDS_ALLOWING_REGEXP = [
|
22
|
-
'and', 'or', 'not', 'while', 'until', 'unless', 'if', 'elsif', 'when'
|
23
|
-
]
|
24
|
-
REGEXP_ALLOWED = WordList.new(false).
|
25
|
-
add(WORDS_ALLOWING_REGEXP, :set)
|
26
|
-
|
27
|
-
PREDEFINED_CONSTANTS = [
|
28
|
-
'nil', 'true', 'false', 'self',
|
29
|
-
'DATA', 'ARGV', 'ARGF', '__FILE__', '__LINE__',
|
30
|
-
]
|
31
|
-
|
32
|
-
IDENT_KIND = WordList.new(:ident).
|
33
|
-
add(RESERVED_WORDS, :reserved).
|
34
|
-
add(PREDEFINED_CONSTANTS, :pre_constant)
|
35
|
-
|
36
|
-
METHOD_NAME = / #{IDENT} [?!]? /xo
|
37
|
-
METHOD_NAME_EX = /
|
38
|
-
#{METHOD_NAME} # common methods: split, foo=, empty?, gsub!
|
39
|
-
| \*\*? # multiplication and power
|
40
|
-
| [-+~]@? # plus, minus
|
41
|
-
| [\/%&|^`] # division, modulo or format strings, &and, |or, ^xor, `system`
|
42
|
-
| \[\]=? # array getter and setter
|
43
|
-
| <=?>? | >=? # comparison, rocket operator
|
44
|
-
| << | >> # append or shift left, shift right
|
45
|
-
| ===? # simple equality and case equality
|
46
|
-
/ox
|
47
|
-
GLOBAL_VARIABLE = / \$ (?: #{IDENT} | \d+ | [~&+`'=\/,;_.<>!@0$?*":F\\] | -[a-zA-Z_0-9] ) /ox
|
48
|
-
|
49
|
-
DOUBLEQ = / " [^"\#\\]* (?: (?: \#\{.*?\} | \#(?:$")? | \\. ) [^"\#\\]* )* "? /ox
|
50
|
-
SINGLEQ = / ' [^'\\]* (?: \\. [^'\\]* )* '? /ox
|
51
|
-
STRING = / #{SINGLEQ} | #{DOUBLEQ} /ox
|
52
|
-
SHELL = / ` [^`\#\\]* (?: (?: \#\{.*?\} | \#(?:$`)? | \\. ) [^`\#\\]* )* `? /ox
|
53
|
-
REGEXP = / \/ [^\/\#\\]* (?: (?: \#\{.*?\} | \#(?:$\/)? | \\. ) [^\/\#\\]* )* \/? /ox
|
54
|
-
|
55
|
-
DECIMAL = /\d+(?:_\d+)*/ # doesn't recognize 09 as octal error
|
56
|
-
OCTAL = /0_?[0-7]+(?:_[0-7]+)*/
|
57
|
-
HEXADECIMAL = /0x[0-9A-Fa-f]+(?:_[0-9A-Fa-f]+)*/
|
58
|
-
BINARY = /0b[01]+(?:_[01]+)*/
|
59
|
-
|
60
|
-
EXPONENT = / [eE] [+-]? #{DECIMAL} /ox
|
61
|
-
FLOAT = / #{DECIMAL} (?: #{EXPONENT} | \. #{DECIMAL} #{EXPONENT}? ) /
|
62
|
-
INTEGER = /#{OCTAL}|#{HEXADECIMAL}|#{BINARY}|#{DECIMAL}/
|
63
|
-
|
64
|
-
def reset
|
65
|
-
super
|
66
|
-
@regexp_allowed = false
|
67
|
-
end
|
68
|
-
|
69
|
-
def next_token
|
70
|
-
return if @scanner.eos?
|
71
|
-
|
72
|
-
kind = :error
|
73
|
-
if @scanner.scan(/\s+/) # in every state
|
74
|
-
kind = :space
|
75
|
-
@regexp_allowed = :set if @regexp_allowed or @scanner.matched.index(?\n) # delayed flag setting
|
76
|
-
|
77
|
-
elsif @state == :def_expected
|
78
|
-
if @scanner.scan(/ (?: (?:#{IDENT}(?:\.|::))* | (?:@@?|$)? #{IDENT}(?:\.|::) ) #{METHOD_NAME_EX} /ox)
|
79
|
-
kind = :method
|
80
|
-
@state = :initial
|
81
|
-
else
|
82
|
-
@scanner.getch
|
83
|
-
end
|
84
|
-
@state = :initial
|
85
|
-
|
86
|
-
elsif @state == :module_expected
|
87
|
-
if @scanner.scan(/<</)
|
88
|
-
kind = :operator
|
89
|
-
else
|
90
|
-
if @scanner.scan(/ (?: #{IDENT} (?:\.|::))* #{IDENT} /ox)
|
91
|
-
kind = :method
|
92
|
-
else
|
93
|
-
@scanner.getch
|
94
|
-
end
|
95
|
-
@state = :initial
|
96
|
-
end
|
97
|
-
|
98
|
-
elsif # state == :initial
|
99
|
-
# IDENTIFIERS, KEYWORDS
|
100
|
-
if @scanner.scan(GLOBAL_VARIABLE)
|
101
|
-
kind = :global_variable
|
102
|
-
elsif @scanner.scan(/ @@ #{IDENT} /ox)
|
103
|
-
kind = :class_variable
|
104
|
-
elsif @scanner.scan(/ @ #{IDENT} /ox)
|
105
|
-
kind = :instance_variable
|
106
|
-
elsif @scanner.scan(/ __END__\n ( (?!\#CODE\#) .* )? | \#[^\n]* | =begin(?=\s).*? \n=end(?=\s|\z)(?:[^\n]*)? /mx)
|
107
|
-
kind = :comment
|
108
|
-
elsif @scanner.scan(METHOD_NAME)
|
109
|
-
if @last_token_dot
|
110
|
-
kind = :ident
|
111
|
-
else
|
112
|
-
matched = @scanner.matched
|
113
|
-
kind = IDENT_KIND[matched]
|
114
|
-
if kind == :ident and matched =~ /^[A-Z]/
|
115
|
-
kind = :constant
|
116
|
-
elsif kind == :reserved
|
117
|
-
@state = DEF_NEW_STATE[matched]
|
118
|
-
@regexp_allowed = REGEXP_ALLOWED[matched]
|
119
|
-
end
|
120
|
-
end
|
121
|
-
|
122
|
-
elsif @scanner.scan(STRING)
|
123
|
-
kind = :string
|
124
|
-
elsif @scanner.scan(SHELL)
|
125
|
-
kind = :shell
|
126
|
-
elsif @scanner.scan(/<<
|
127
|
-
(?:
|
128
|
-
([a-zA-Z_0-9]+)
|
129
|
-
(?: .*? ^\1$ | .* )
|
130
|
-
|
|
131
|
-
-([a-zA-Z_0-9]+)
|
132
|
-
(?: .*? ^\s*\2$ | .* )
|
133
|
-
|
|
134
|
-
(["\'`]) (.+?) \3
|
135
|
-
(?: .*? ^\4$ | .* )
|
136
|
-
|
|
137
|
-
- (["\'`]) (.+?) \5
|
138
|
-
(?: .*? ^\s*\6$ | .* )
|
139
|
-
)
|
140
|
-
/mxo)
|
141
|
-
kind = :string
|
142
|
-
elsif @scanner.scan(/\//) and @regexp_allowed
|
143
|
-
@scanner.unscan
|
144
|
-
@scanner.scan(REGEXP)
|
145
|
-
kind = :regexp
|
146
|
-
/%(?:[Qqxrw](?:\([^)#\\\\]*(?:(?:#\{.*?\}|#|\\\\.)[^)#\\\\]*)*\)?|\[[^\]#\\\\]*(?:(?:#\{.*?\}|#|\\\\.)[^\]#\\\\]*)*\]?|\{[^}#\\\\]*(?:(?:#\{.*?\}|#|\\\\.)[^}#\\\\]*)*\}?|<[^>#\\\\]*(?:(?:#\{.*?\}|#|\\\\.)[^>#\\\\]*)*>?|([^a-zA-Z\\\\])(?:(?!\1)[^#\\\\])*(?:(?:#\{.*?\}|#|\\\\.)(?:(?!\1)[^#\\\\])*)*\1?)|\([^)#\\\\]*(?:(?:#\{.*?\}|#|\\\\.)[^)#\\\\]*)*\)?|\[[^\]#\\\\]*(?:(?:#\{.*?\}|#|\\\\.)[^\]#\\\\]*)*\]?|\{[^}#\\\\]*(?:(?:#\{.*?\}|#|\\\\.)[^}#\\\\]*)*\}?|<[^>#\\\\]*(?:(?:#\{.*?\}|#|\\\\.)[^>#\\\\]*)*>?|([^a-zA-Z\s\\\\])(?:(?!\2)[^#\\\\])*(?:(?:#\{.*?\}|#|\\\\.)(?:(?!\2)[^#\\\\])*)*\2?|\\\\[^#\\\\]*(?:(?:#\{.*?\}|#)[^#\\\\]*)*\\\\?)/
|
147
|
-
elsif @scanner.scan(/:(?:#{GLOBAL_VARIABLE}|#{METHOD_NAME_EX}|#{STRING})/ox)
|
148
|
-
kind = :symbol
|
149
|
-
elsif @scanner.scan(/
|
150
|
-
\? (?:
|
151
|
-
[^\s\\]
|
152
|
-
|
|
153
|
-
\\ (?:M-\\C-|C-\\M-|M-\\c|c\\M-|c|C-|M-))? (?: \\ (?: . | [0-7]{3} | x[0-9A-Fa-f][0-9A-Fa-f] )
|
154
|
-
)
|
155
|
-
/mox)
|
156
|
-
kind = :integer
|
157
|
-
|
158
|
-
elsif @scanner.scan(/ [-+*\/%=<>;,|&!()\[\]{}~?] | \.\.?\.? | ::? /x)
|
159
|
-
kind = :operator
|
160
|
-
@regexp_allowed = :set if @scanner.matched[-1,1] =~ /[~=!<>|&^,\(\[+\-\/\*%]\z/
|
161
|
-
elsif @scanner.scan(FLOAT)
|
162
|
-
kind = :float
|
163
|
-
elsif @scanner.scan(INTEGER)
|
164
|
-
kind = :integer
|
165
|
-
else
|
166
|
-
@scanner.getch
|
167
|
-
end
|
168
|
-
end
|
169
|
-
|
170
|
-
token = Token.new @scanner.matched, kind
|
171
|
-
|
172
|
-
if kind == :regexp
|
173
|
-
token.text << @scanner.scan(/[eimnosux]*/)
|
174
|
-
end
|
175
|
-
|
176
|
-
@regexp_allowed = (@regexp_allowed == :set) # delayed flag setting
|
177
|
-
|
178
|
-
token
|
179
|
-
end
|
180
|
-
end
|
181
|
-
|
182
|
-
register Ruby, 'ruby', 'rb'
|
183
|
-
|
184
|
-
end
|
185
|
-
end
|
186
|
-
class Set
|
187
|
-
include Enumerable
|
188
|
-
|
189
|
-
# Creates a new set containing the given objects.
|
190
|
-
def self.[](*ary)
|
191
|
-
new(ary)
|
192
|
-
end
|
193
|
-
|
194
|
-
# Creates a new set containing the elements of the given enumerable
|
195
|
-
# object.
|
196
|
-
#
|
197
|
-
# If a block is given, the elements of enum are preprocessed by the
|
198
|
-
# given block.
|
199
|
-
def initialize(enum = nil, &block) # :yields: o
|
200
|
-
@hash ||= Hash.new
|
201
|
-
|
202
|
-
enum.nil? and return
|
203
|
-
|
204
|
-
if block
|
205
|
-
enum.each { |o| add(block[o]) }
|
206
|
-
else
|
207
|
-
merge(enum)
|
208
|
-
end
|
209
|
-
end
|
210
|
-
|
211
|
-
# Copy internal hash.
|
212
|
-
def initialize_copy(orig)
|
213
|
-
@hash = orig.instance_eval{@hash}.dup
|
214
|
-
end
|
215
|
-
|
216
|
-
# Returns the number of elements.
|
217
|
-
def size
|
218
|
-
@hash.size
|
219
|
-
end
|
220
|
-
alias length size
|
221
|
-
|
222
|
-
# Returns true if the set contains no elements.
|
223
|
-
def empty?
|
224
|
-
@hash.empty?
|
225
|
-
end
|
226
|
-
|
227
|
-
# Removes all elements and returns self.
|
228
|
-
def clear
|
229
|
-
@hash.clear
|
230
|
-
self
|
231
|
-
end
|
232
|
-
|
233
|
-
# Replaces the contents of the set with the contents of the given
|
234
|
-
# enumerable object and returns self.
|
235
|
-
def replace(enum)
|
236
|
-
if enum.class == self.class
|
237
|
-
@hash.replace(enum.instance_eval { @hash })
|
238
|
-
else
|
239
|
-
enum.is_a?(Enumerable) or raise ArgumentError, "value must be enumerable"
|
240
|
-
clear
|
241
|
-
enum.each { |o| add(o) }
|
242
|
-
end
|
243
|
-
|
244
|
-
self
|
245
|
-
end
|
246
|
-
|
247
|
-
# Converts the set to an array. The order of elements is uncertain.
|
248
|
-
def to_a
|
249
|
-
@hash.keys
|
250
|
-
end
|
251
|
-
|
252
|
-
def flatten_merge(set, seen = Set.new)
|
253
|
-
set.each { |e|
|
254
|
-
if e.is_a?(Set)
|
255
|
-
if seen.include?(e_id = e.object_id)
|
256
|
-
raise ArgumentError, "tried to flatten recursive Set"
|
257
|
-
end
|
258
|
-
|
259
|
-
seen.add(e_id)
|
260
|
-
flatten_merge(e, seen)
|
261
|
-
seen.delete(e_id)
|
262
|
-
else
|
263
|
-
add(e)
|
264
|
-
end
|
265
|
-
}
|
266
|
-
|
267
|
-
self
|
268
|
-
end
|
269
|
-
protected :flatten_merge
|
270
|
-
|
271
|
-
# Returns a new set that is a copy of the set, flattening each
|
272
|
-
# containing set recursively.
|
273
|
-
def flatten
|
274
|
-
self.class.new.flatten_merge(self)
|
275
|
-
end
|
276
|
-
|
277
|
-
# Equivalent to Set#flatten, but replaces the receiver with the
|
278
|
-
# result in place. Returns nil if no modifications were made.
|
279
|
-
def flatten!
|
280
|
-
if detect { |e| e.is_a?(Set) }
|
281
|
-
replace(flatten())
|
282
|
-
else
|
283
|
-
nil
|
284
|
-
end
|
285
|
-
end
|
286
|
-
|
287
|
-
# Returns true if the set contains the given object.
|
288
|
-
def include?(o)
|
289
|
-
@hash.include?(o)
|
290
|
-
end
|
291
|
-
alias member? include?
|
292
|
-
|
293
|
-
# Returns true if the set is a superset of the given set.
|
294
|
-
def superset?(set)
|
295
|
-
set.is_a?(Set) or raise ArgumentError, "value must be a set"
|
296
|
-
return false if size < set.size
|
297
|
-
set.all? { |o| include?(o) }
|
298
|
-
end
|
299
|
-
|
300
|
-
# Returns true if the set is a proper superset of the given set.
|
301
|
-
def proper_superset?(set)
|
302
|
-
set.is_a?(Set) or raise ArgumentError, "value must be a set"
|
303
|
-
return false if size <= set.size
|
304
|
-
set.all? { |o| include?(o) }
|
305
|
-
end
|
306
|
-
|
307
|
-
# Returns true if the set is a subset of the given set.
|
308
|
-
def subset?(set)
|
309
|
-
set.is_a?(Set) or raise ArgumentError, "value must be a set"
|
310
|
-
return false if set.size < size
|
311
|
-
all? { |o| set.include?(o) }
|
312
|
-
end
|
313
|
-
|
314
|
-
# Returns true if the set is a proper subset of the given set.
|
315
|
-
def proper_subset?(set)
|
316
|
-
set.is_a?(Set) or raise ArgumentError, "value must be a set"
|
317
|
-
return false if set.size <= size
|
318
|
-
all? { |o| set.include?(o) }
|
319
|
-
end
|
320
|
-
|
321
|
-
# Calls the given block once for each element in the set, passing
|
322
|
-
# the element as parameter.
|
323
|
-
def each
|
324
|
-
@hash.each_key { |o| yield(o) }
|
325
|
-
self
|
326
|
-
end
|
327
|
-
|
328
|
-
# Adds the given object to the set and returns self. Use +merge+ to
|
329
|
-
# add several elements at once.
|
330
|
-
def add(o)
|
331
|
-
@hash[o] = true
|
332
|
-
self
|
333
|
-
end
|
334
|
-
alias << add
|
335
|
-
|
336
|
-
# Adds the given object to the set and returns self. If the
|
337
|
-
# object is already in the set, returns nil.
|
338
|
-
def add?(o)
|
339
|
-
if include?(o)
|
340
|
-
nil
|
341
|
-
else
|
342
|
-
add(o)
|
343
|
-
end
|
344
|
-
end
|
345
|
-
|
346
|
-
# Deletes the given object from the set and returns self. Use +subtract+ to
|
347
|
-
# delete several items at once.
|
348
|
-
def delete(o)
|
349
|
-
@hash.delete(o)
|
350
|
-
self
|
351
|
-
end
|
352
|
-
|
353
|
-
# Deletes the given object from the set and returns self. If the
|
354
|
-
# object is not in the set, returns nil.
|
355
|
-
def delete?(o)
|
356
|
-
if include?(o)
|
357
|
-
delete(o)
|
358
|
-
else
|
359
|
-
nil
|
360
|
-
end
|
361
|
-
end
|
362
|
-
|
363
|
-
# Deletes every element of the set for which block evaluates to
|
364
|
-
# true, and returns self.
|
365
|
-
def delete_if
|
366
|
-
@hash.delete_if { |o,| yield(o) }
|
367
|
-
self
|
368
|
-
end
|
369
|
-
|
370
|
-
# Do collect() destructively.
|
371
|
-
def collect!
|
372
|
-
set = self.class.new
|
373
|
-
each { |o| set << yield(o) }
|
374
|
-
replace(set)
|
375
|
-
end
|
376
|
-
alias map! collect!
|
377
|
-
|
378
|
-
# Equivalent to Set#delete_if, but returns nil if no changes were
|
379
|
-
# made.
|
380
|
-
def reject!
|
381
|
-
n = size
|
382
|
-
delete_if { |o| yield(o) }
|
383
|
-
size == n ? nil : self
|
384
|
-
end
|
385
|
-
|
386
|
-
# Merges the elements of the given enumerable object to the set and
|
387
|
-
# returns self.
|
388
|
-
def merge(enum)
|
389
|
-
if enum.is_a?(Set)
|
390
|
-
@hash.update(enum.instance_eval { @hash })
|
391
|
-
else
|
392
|
-
enum.is_a?(Enumerable) or raise ArgumentError, "value must be enumerable"
|
393
|
-
enum.each { |o| add(o) }
|
394
|
-
end
|
395
|
-
|
396
|
-
self
|
397
|
-
end
|
398
|
-
|
399
|
-
# Deletes every element that appears in the given enumerable object
|
400
|
-
# and returns self.
|
401
|
-
def subtract(enum)
|
402
|
-
enum.is_a?(Enumerable) or raise ArgumentError, "value must be enumerable"
|
403
|
-
enum.each { |o| delete(o) }
|
404
|
-
self
|
405
|
-
end
|
406
|
-
|
407
|
-
# Returns a new set built by merging the set and the elements of the
|
408
|
-
# given enumerable object.
|
409
|
-
def |(enum)
|
410
|
-
enum.is_a?(Enumerable) or raise ArgumentError, "value must be enumerable"
|
411
|
-
dup.merge(enum)
|
412
|
-
end
|
413
|
-
alias + | ##
|
414
|
-
alias union | ##
|
415
|
-
|
416
|
-
# Returns a new set built by duplicating the set, removing every
|
417
|
-
# element that appears in the given enumerable object.
|
418
|
-
def -(enum)
|
419
|
-
enum.is_a?(Enumerable) or raise ArgumentError, "value must be enumerable"
|
420
|
-
dup.subtract(enum)
|
421
|
-
end
|
422
|
-
alias difference - ##
|
423
|
-
|
424
|
-
# Returns a new array containing elements common to the set and the
|
425
|
-
# given enumerable object.
|
426
|
-
def &(enum)
|
427
|
-
enum.is_a?(Enumerable) or raise ArgumentError, "value must be enumerable"
|
428
|
-
n = self.class.new
|
429
|
-
enum.each { |o| n.add(o) if include?(o) }
|
430
|
-
n
|
431
|
-
end
|
432
|
-
alias intersection & ##
|
433
|
-
|
434
|
-
# Returns a new array containing elements exclusive between the set
|
435
|
-
# and the given enumerable object. (set ^ enum) is equivalent to
|
436
|
-
# ((set | enum) - (set & enum)).
|
437
|
-
def ^(enum)
|
438
|
-
enum.is_a?(Enumerable) or raise ArgumentError, "value must be enumerable"
|
439
|
-
n = dup
|
440
|
-
enum.each { |o| if n.include?(o) then n.delete(o) else n.add(o) end }
|
441
|
-
n
|
442
|
-
end
|
443
|
-
|
444
|
-
# Returns true if two sets are equal. The equality of each couple
|
445
|
-
# of elements is defined according to Object#eql?.
|
446
|
-
def ==(set)
|
447
|
-
equal?(set) and return true
|
448
|
-
|
449
|
-
set.is_a?(Set) && size == set.size or return false
|
450
|
-
|
451
|
-
hash = @hash.dup
|
452
|
-
set.all? { |o| hash.include?(o) }
|
453
|
-
end
|
454
|
-
|
455
|
-
def hash # :nodoc:
|
456
|
-
@hash.hash
|
457
|
-
end
|
458
|
-
|
459
|
-
def eql?(o) # :nodoc:
|
460
|
-
return false unless o.is_a?(Set)
|
461
|
-
@hash.eql?(o.instance_eval{@hash})
|
462
|
-
end
|
463
|
-
|
464
|
-
# Classifies the set by the return value of the given block and
|
465
|
-
# returns a hash of {value => set of elements} pairs. The block is
|
466
|
-
# called once for each element of the set, passing the element as
|
467
|
-
# parameter.
|
468
|
-
#
|
469
|
-
# e.g.:
|
470
|
-
#
|
471
|
-
# require 'set'
|
472
|
-
# files = Set.new(Dir.glob("*.rb"))
|
473
|
-
# hash = files.classify { |f| File.mtime(f).year }
|
474
|
-
# p hash # => {2000=>#<Set: {"a.rb", "b.rb"}>,
|
475
|
-
# # 2001=>#<Set: {"c.rb", "d.rb", "e.rb"}>,
|
476
|
-
# # 2002=>#<Set: {"f.rb"}>}
|
477
|
-
def classify # :yields: o
|
478
|
-
h = {}
|
479
|
-
|
480
|
-
each { |i|
|
481
|
-
x = yield(i)
|
482
|
-
(h[x] ||= self.class.new).add(i)
|
483
|
-
}
|
484
|
-
|
485
|
-
h
|
486
|
-
end
|
487
|
-
|
488
|
-
# Divides the set into a set of subsets according to the commonality
|
489
|
-
# defined by the given block.
|
490
|
-
#
|
491
|
-
# If the arity of the block is 2, elements o1 and o2 are in common
|
492
|
-
# if block.call(o1, o2) is true. Otherwise, elements o1 and o2 are
|
493
|
-
# in common if block.call(o1) == block.call(o2).
|
494
|
-
#
|
495
|
-
# e.g.:
|
496
|
-
#
|
497
|
-
# require 'set'
|
498
|
-
# numbers = Set[1, 3, 4, 6, 9, 10, 11]
|
499
|
-
# set = numbers.divide { |i,j| (i - j).abs == 1 }
|
500
|
-
# p set # => #<Set: {#<Set: {1}>,
|
501
|
-
# # #<Set: {11, 9, 10}>,
|
502
|
-
# # #<Set: {3, 4}>,
|
503
|
-
# # #<Set: {6}>}>
|
504
|
-
def divide(&func)
|
505
|
-
if func.arity == 2
|
506
|
-
require 'tsort'
|
507
|
-
|
508
|
-
class << dig = {} # :nodoc:
|
509
|
-
include TSort
|
510
|
-
|
511
|
-
alias tsort_each_node each_key
|
512
|
-
def tsort_each_child(node, &block)
|
513
|
-
fetch(node).each(&block)
|
514
|
-
end
|
515
|
-
end
|
516
|
-
|
517
|
-
each { |u|
|
518
|
-
dig[u] = a = []
|
519
|
-
each{ |v| func.call(u, v) and a << v }
|
520
|
-
}
|
521
|
-
|
522
|
-
set = Set.new()
|
523
|
-
dig.each_strongly_connected_component { |css|
|
524
|
-
set.add(self.class.new(css))
|
525
|
-
}
|
526
|
-
set
|
527
|
-
else
|
528
|
-
Set.new(classify(&func).values)
|
529
|
-
end
|
530
|
-
end
|
531
|
-
|
532
|
-
InspectKey = :__inspect_key__ # :nodoc:
|
533
|
-
|
534
|
-
# Returns a string containing a human-readable representation of the
|
535
|
-
# set. ("#<Set: {element1, element2, ...}>")
|
536
|
-
def inspect
|
537
|
-
ids = (Thread.current[InspectKey] ||= [])
|
538
|
-
|
539
|
-
if ids.include?(object_id)
|
540
|
-
return sprintf('#<%s: {...}>', self.class.name)
|
541
|
-
end
|
542
|
-
|
543
|
-
begin
|
544
|
-
ids << object_id
|
545
|
-
return sprintf('#<%s: {%s}>', self.class, to_a.inspect[1..-2])
|
546
|
-
ensure
|
547
|
-
ids.pop
|
548
|
-
end
|
549
|
-
end
|
550
|
-
|
551
|
-
def pretty_print(pp) # :nodoc:
|
552
|
-
pp.text sprintf('#<%s: {', self.class.name)
|
553
|
-
pp.nest(1) {
|
554
|
-
pp.seplist(self) { |o|
|
555
|
-
pp.pp o
|
556
|
-
}
|
557
|
-
}
|
558
|
-
pp.text "}>"
|
559
|
-
end
|
560
|
-
|
561
|
-
def pretty_print_cycle(pp) # :nodoc:
|
562
|
-
pp.text sprintf('#<%s: {%s}>', self.class.name, empty? ? '' : '...')
|
563
|
-
end
|
564
|
-
end
|
565
|
-
|
566
|
-
# SortedSet implements a set which elements are sorted in order. See Set.
|
567
|
-
class SortedSet < Set
|
568
|
-
@@setup = false
|
569
|
-
|
570
|
-
class << self
|
571
|
-
def [](*ary) # :nodoc:
|
572
|
-
new(ary)
|
573
|
-
end
|
574
|
-
|
575
|
-
def setup # :nodoc:
|
576
|
-
@@setup and return
|
577
|
-
|
578
|
-
begin
|
579
|
-
require 'rbtree'
|
580
|
-
|
581
|
-
module_eval %{
|
582
|
-
def initialize(*args, &block)
|
583
|
-
@hash = RBTree.new
|
584
|
-
super
|
585
|
-
end
|
586
|
-
}
|
587
|
-
rescue LoadError
|
588
|
-
module_eval %{
|
589
|
-
def initialize(*args, &block)
|
590
|
-
@keys = nil
|
591
|
-
super
|
592
|
-
end
|
593
|
-
|
594
|
-
def clear
|
595
|
-
@keys = nil
|
596
|
-
super
|
597
|
-
end
|
598
|
-
|
599
|
-
def replace(enum)
|
600
|
-
@keys = nil
|
601
|
-
super
|
602
|
-
end
|
603
|
-
|
604
|
-
def add(o)
|
605
|
-
@keys = nil
|
606
|
-
@hash[o] = true
|
607
|
-
self
|
608
|
-
end
|
609
|
-
alias << add
|
610
|
-
|
611
|
-
def delete(o)
|
612
|
-
@keys = nil
|
613
|
-
@hash.delete(o)
|
614
|
-
self
|
615
|
-
end
|
616
|
-
|
617
|
-
def delete_if
|
618
|
-
n = @hash.size
|
619
|
-
@hash.delete_if { |o,| yield(o) }
|
620
|
-
@keys = nil if @hash.size != n
|
621
|
-
self
|
622
|
-
end
|
623
|
-
|
624
|
-
def merge(enum)
|
625
|
-
@keys = nil
|
626
|
-
super
|
627
|
-
end
|
628
|
-
|
629
|
-
def each
|
630
|
-
to_a.each { |o| yield(o) }
|
631
|
-
end
|
632
|
-
|
633
|
-
def to_a
|
634
|
-
(@keys = @hash.keys).sort! unless @keys
|
635
|
-
@keys
|
636
|
-
end
|
637
|
-
}
|
638
|
-
end
|
639
|
-
|
640
|
-
@@setup = true
|
641
|
-
end
|
642
|
-
end
|
643
|
-
|
644
|
-
def initialize(*args, &block) # :nodoc:
|
645
|
-
SortedSet.setup
|
646
|
-
initialize(*args, &block)
|
647
|
-
end
|
648
|
-
end
|
649
|
-
|
650
|
-
module Enumerable
|
651
|
-
# Makes a set from the enumerable object with given arguments.
|
652
|
-
def to_set(klass = Set, *args, &block)
|
653
|
-
klass.new(self, *args, &block)
|
654
|
-
end
|
655
|
-
end
|
656
|
-
|
657
|
-
# =begin
|
658
|
-
# == RestricedSet class
|
659
|
-
# RestricedSet implements a set with restrictions defined by a given
|
660
|
-
# block.
|
661
|
-
#
|
662
|
-
# === Super class
|
663
|
-
# Set
|
664
|
-
#
|
665
|
-
# === Class Methods
|
666
|
-
# --- RestricedSet::new(enum = nil) { |o| ... }
|
667
|
-
# --- RestricedSet::new(enum = nil) { |rset, o| ... }
|
668
|
-
# Creates a new restricted set containing the elements of the given
|
669
|
-
# enumerable object. Restrictions are defined by the given block.
|
670
|
-
#
|
671
|
-
# If the block's arity is 2, it is called with the RestrictedSet
|
672
|
-
# itself and an object to see if the object is allowed to be put in
|
673
|
-
# the set.
|
674
|
-
#
|
675
|
-
# Otherwise, the block is called with an object to see if the object
|
676
|
-
# is allowed to be put in the set.
|
677
|
-
#
|
678
|
-
# === Instance Methods
|
679
|
-
# --- restriction_proc
|
680
|
-
# Returns the restriction procedure of the set.
|
681
|
-
#
|
682
|
-
# =end
|
683
|
-
#
|
684
|
-
# class RestricedSet < Set
|
685
|
-
# def initialize(*args, &block)
|
686
|
-
# @proc = block or raise ArgumentError, "missing a block"
|
687
|
-
#
|
688
|
-
# if @proc.arity == 2
|
689
|
-
# instance_eval %{
|
690
|
-
# def add(o)
|
691
|
-
# @hash[o] = true if @proc.call(self, o)
|
692
|
-
# self
|
693
|
-
# end
|
694
|
-
# alias << add
|
695
|
-
#
|
696
|
-
# def add?(o)
|
697
|
-
# if include?(o) || !@proc.call(self, o)
|
698
|
-
# nil
|
699
|
-
# else
|
700
|
-
# @hash[o] = true
|
701
|
-
# self
|
702
|
-
# end
|
703
|
-
# end
|
704
|
-
#
|
705
|
-
# def replace(enum)
|
706
|
-
# enum.is_a?(Enumerable) or raise ArgumentError, "value must be enumerable"
|
707
|
-
# clear
|
708
|
-
# enum.each { |o| add(o) }
|
709
|
-
#
|
710
|
-
# self
|
711
|
-
# end
|
712
|
-
#
|
713
|
-
# def merge(enum)
|
714
|
-
# enum.is_a?(Enumerable) or raise ArgumentError, "value must be enumerable"
|
715
|
-
# enum.each { |o| add(o) }
|
716
|
-
#
|
717
|
-
# self
|
718
|
-
# end
|
719
|
-
# }
|
720
|
-
# else
|
721
|
-
# instance_eval %{
|
722
|
-
# def add(o)
|
723
|
-
# if @proc.call(o)
|
724
|
-
# @hash[o] = true
|
725
|
-
# end
|
726
|
-
# self
|
727
|
-
# end
|
728
|
-
# alias << add
|
729
|
-
#
|
730
|
-
# def add?(o)
|
731
|
-
# if include?(o) || !@proc.call(o)
|
732
|
-
# nil
|
733
|
-
# else
|
734
|
-
# @hash[o] = true
|
735
|
-
# self
|
736
|
-
# end
|
737
|
-
# end
|
738
|
-
# }
|
739
|
-
# end
|
740
|
-
#
|
741
|
-
# super(*args)
|
742
|
-
# end
|
743
|
-
#
|
744
|
-
# def restriction_proc
|
745
|
-
# @proc
|
746
|
-
# end
|
747
|
-
# end
|
748
|
-
|
749
|
-
if $0 == __FILE__
|
750
|
-
eval DATA.read, nil, $0, __LINE__+4
|
751
|
-
end
|
752
|
-
|
753
|
-
# = rweb - CGI Support Library
|
754
|
-
#
|
755
|
-
# Author:: Johannes Barre (mailto:rweb@igels.net)
|
756
|
-
# Copyright:: Copyright (c) 2003, 04 by Johannes Barre
|
757
|
-
# License:: GNU Lesser General Public License (COPYING, http://www.gnu.org/copyleft/lesser.html)
|
758
|
-
# Version:: 0.1.0
|
759
|
-
# CVS-ID:: $Id: example.rb 39 2005-11-05 03:33:55Z murphy $
|
760
|
-
#
|
761
|
-
# == What is Rweb?
|
762
|
-
# Rweb is a replacement for the cgi class included in the ruby distribution.
|
763
|
-
#
|
764
|
-
# == How to use
|
765
|
-
#
|
766
|
-
# === Basics
|
767
|
-
#
|
768
|
-
# This class is made to be as easy as possible to use. An example:
|
769
|
-
#
|
770
|
-
# require "rweb"
|
771
|
-
#
|
772
|
-
# web = Rweb.new
|
773
|
-
# web.out do
|
774
|
-
# web.puts "Hello world!"
|
775
|
-
# end
|
776
|
-
#
|
777
|
-
# The visitor will get a simple "Hello World!" in his browser. Please notice,
|
778
|
-
# that won't set html-tags for you, so you should better do something like this:
|
779
|
-
#
|
780
|
-
# require "rweb"
|
781
|
-
#
|
782
|
-
# web = Rweb.new
|
783
|
-
# web.out do
|
784
|
-
# web.puts "<html><body>Hello world!</body></html>"
|
785
|
-
# end
|
786
|
-
#
|
787
|
-
# === Set headers
|
788
|
-
# Of course, it's also possible to tell the browser, that the content of this
|
789
|
-
# page is plain text instead of html code:
|
790
|
-
#
|
791
|
-
# require "rweb"
|
792
|
-
#
|
793
|
-
# web = Rweb.new
|
794
|
-
# web.out do
|
795
|
-
# web.header("content-type: text/plain")
|
796
|
-
# web.puts "Hello plain world!"
|
797
|
-
# end
|
798
|
-
#
|
799
|
-
# Please remember, headers can't be set after the page content has been send.
|
800
|
-
# You have to set all nessessary headers before the first puts oder print. It's
|
801
|
-
# possible to cache the content until everything is complete. Doing it this
|
802
|
-
# way, you can set headers everywhere.
|
803
|
-
#
|
804
|
-
# If you set a header twice, the second header will replace the first one. The
|
805
|
-
# header name is not casesensitive, it will allways converted in to the
|
806
|
-
# capitalised form suggested by the w3c (http://w3.org)
|
807
|
-
#
|
808
|
-
# === Set cookies
|
809
|
-
# Setting cookies is quite easy:
|
810
|
-
# include 'rweb'
|
811
|
-
#
|
812
|
-
# web = Rweb.new
|
813
|
-
# Cookie.new("Visits", web.cookies['visits'].to_i +1)
|
814
|
-
# web.out do
|
815
|
-
# web.puts "Welcome back! You visited this page #{web.cookies['visits'].to_i +1} times"
|
816
|
-
# end
|
817
|
-
#
|
818
|
-
# See the class Cookie for more details.
|
819
|
-
#
|
820
|
-
# === Get form and cookie values
|
821
|
-
# There are four ways to submit data from the browser to the server and your
|
822
|
-
# ruby script: via GET, POST, cookies and file upload. Rweb doesn't support
|
823
|
-
# file upload by now.
|
824
|
-
#
|
825
|
-
# include 'rweb'
|
826
|
-
#
|
827
|
-
# web = Rweb.new
|
828
|
-
# web.out do
|
829
|
-
# web.print "action: #{web.get['action']} "
|
830
|
-
# web.puts "The value of the cookie 'visits' is #{web.cookies['visits']}"
|
831
|
-
# web.puts "The post parameter 'test['x']' is #{web.post['test']['x']}"
|
832
|
-
# end
|
833
|
-
|
834
|
-
RWEB_VERSION = "0.1.0"
|
835
|
-
RWEB = "rweb/#{RWEB_VERSION}"
|
836
|
-
|
837
|
-
#require 'rwebcookie' -> edit by bunny :-)
|
838
|
-
|
839
|
-
class Rweb
|
840
|
-
# All parameter submitted via the GET method are available in attribute
|
841
|
-
# get. This is Hash, where every parameter is available as a key-value
|
842
|
-
# pair.
|
843
|
-
#
|
844
|
-
# If your input tag has a name like this one, it's value will be available
|
845
|
-
# as web.get["fieldname"]
|
846
|
-
# <input name="fieldname">
|
847
|
-
# You can submit values as a Hash
|
848
|
-
# <input name="text['index']">
|
849
|
-
# <input name="text['index2']">
|
850
|
-
# will be available as
|
851
|
-
# web.get["text"]["index"]
|
852
|
-
# web.get["text"]["index2"]
|
853
|
-
# Integers are also possible
|
854
|
-
# <input name="int[2]">
|
855
|
-
# <input name="int[3]['hi']>
|
856
|
-
# will be available as
|
857
|
-
# web.get["int"][2]
|
858
|
-
# web.get["int"][3]["hi"]
|
859
|
-
# If you specify no index, the lowest unused index will be used:
|
860
|
-
# <input name="int[]"><!-- First Field -->
|
861
|
-
# <input name="int[]"><!-- Second one -->
|
862
|
-
# will be available as
|
863
|
-
# web.get["int"][0] # First Field
|
864
|
-
# web.get["int"][1] # Second one
|
865
|
-
# Please notice, this doesn'd work like you might expect:
|
866
|
-
# <input name="text[index]">
|
867
|
-
# It will not be available as web.get["text"]["index"] but
|
868
|
-
# web.get["text[index]"]
|
869
|
-
attr_reader :get
|
870
|
-
|
871
|
-
# All parameters submitted via POST are available in the attribute post. It
|
872
|
-
# works like the get attribute.
|
873
|
-
# <input name="text[0]">
|
874
|
-
# will be available as
|
875
|
-
# web.post["text"][0]
|
876
|
-
attr_reader :post
|
877
|
-
|
878
|
-
# All cookies submitted by the browser are available in cookies. This is a
|
879
|
-
# Hash, where every cookie is a key-value pair.
|
880
|
-
attr_reader :cookies
|
881
|
-
|
882
|
-
# The name of the browser identification is submitted as USER_AGENT and
|
883
|
-
# available in this attribute.
|
884
|
-
attr_reader :user_agent
|
885
|
-
|
886
|
-
# The IP address of the client.
|
887
|
-
attr_reader :remote_addr
|
888
|
-
|
889
|
-
# Creates a new Rweb object. This should only done once. You can set various
|
890
|
-
# options via the settings hash.
|
891
|
-
#
|
892
|
-
# "cache" => true: Everything you script send to the client will be cached
|
893
|
-
# until the end of the out block or until flush is called. This way, you
|
894
|
-
# can modify headers and cookies even after printing something to the client.
|
895
|
-
#
|
896
|
-
# "safe" => level: Changes the $SAFE attribute. By default, $SAFE will be set
|
897
|
-
# to 1. If $SAFE is already higher than this value, it won't be changed.
|
898
|
-
#
|
899
|
-
# "silend" => true: Normaly, Rweb adds automaticly a header like this
|
900
|
-
# "X-Powered-By: Rweb/x.x.x (Ruby/y.y.y)". With the silend option you can
|
901
|
-
# suppress this.
|
902
|
-
def initialize (settings = {})
|
903
|
-
# {{{
|
904
|
-
@header = {}
|
905
|
-
@cookies = {}
|
906
|
-
@get = {}
|
907
|
-
@post = {}
|
908
|
-
|
909
|
-
# Internal attributes
|
910
|
-
@status = nil
|
911
|
-
@reasonPhrase = nil
|
912
|
-
@setcookies = []
|
913
|
-
@output_started = false;
|
914
|
-
@output_allowed = false;
|
915
|
-
|
916
|
-
@mod_ruby = false
|
917
|
-
@env = ENV.to_hash
|
918
|
-
|
919
|
-
if defined?(MOD_RUBY)
|
920
|
-
@output_method = "mod_ruby"
|
921
|
-
@mod_ruby = true
|
922
|
-
elsif @env['SERVER_SOFTWARE'] =~ /^Microsoft-IIS/i
|
923
|
-
@output_method = "nph"
|
924
|
-
else
|
925
|
-
@output_method = "ph"
|
926
|
-
end
|
927
|
-
|
928
|
-
unless settings.is_a?(Hash)
|
929
|
-
raise TypeError, "settings must be a Hash"
|
930
|
-
end
|
931
|
-
@settings = settings
|
932
|
-
|
933
|
-
unless @settings.has_key?("safe")
|
934
|
-
@settings["safe"] = 1
|
935
|
-
end
|
936
|
-
|
937
|
-
if $SAFE < @settings["safe"]
|
938
|
-
$SAFE = @settings["safe"]
|
939
|
-
end
|
940
|
-
|
941
|
-
unless @settings.has_key?("cache")
|
942
|
-
@settings["cache"] = false
|
943
|
-
end
|
944
|
-
|
945
|
-
# mod_ruby sets no QUERY_STRING variable, if no GET-Parameters are given
|
946
|
-
unless @env.has_key?("QUERY_STRING")
|
947
|
-
@env["QUERY_STRING"] = ""
|
948
|
-
end
|
949
|
-
|
950
|
-
# Now we split the QUERY_STRING by the seperators & and ; or, if
|
951
|
-
# specified, settings['get seperator']
|
952
|
-
unless @settings.has_key?("get seperator")
|
953
|
-
get_args = @env['QUERY_STRING'].split(/[&;]/)
|
954
|
-
else
|
955
|
-
get_args = @env['QUERY_STRING'].split(@settings['get seperator'])
|
956
|
-
end
|
957
|
-
|
958
|
-
get_args.each do | arg |
|
959
|
-
arg_key, arg_val = arg.split(/=/, 2)
|
960
|
-
arg_key = Rweb::unescape(arg_key)
|
961
|
-
arg_val = Rweb::unescape(arg_val)
|
962
|
-
|
963
|
-
# Parse names like name[0], name['text'] or name[]
|
964
|
-
pattern = /^(.+)\[("[^\]]*"|'[^\]]*'|[0-9]*)\]$/
|
965
|
-
keys = []
|
966
|
-
while match = pattern.match(arg_key)
|
967
|
-
arg_key = match[1]
|
968
|
-
keys = [match[2]] + keys
|
969
|
-
end
|
970
|
-
keys = [arg_key] + keys
|
971
|
-
|
972
|
-
akt = @get
|
973
|
-
last = nil
|
974
|
-
lastkey = nil
|
975
|
-
keys.each do |key|
|
976
|
-
if key == ""
|
977
|
-
# No key specified (like in "test[]"), so we use the
|
978
|
-
# lowerst unused Integer as key
|
979
|
-
key = 0
|
980
|
-
while akt.has_key?(key)
|
981
|
-
key += 1
|
982
|
-
end
|
983
|
-
elsif /^[0-9]*$/ =~ key
|
984
|
-
# If the index is numerical convert it to an Integer
|
985
|
-
key = key.to_i
|
986
|
-
elsif key[0].chr == "'" || key[0].chr == '"'
|
987
|
-
key = key[1, key.length() -2]
|
988
|
-
end
|
989
|
-
if !akt.has_key?(key) || !akt[key].class == Hash
|
990
|
-
# create an empty Hash if there isn't already one
|
991
|
-
akt[key] = {}
|
992
|
-
end
|
993
|
-
last = akt
|
994
|
-
lastkey = key
|
995
|
-
akt = akt[key]
|
996
|
-
end
|
997
|
-
last[lastkey] = arg_val
|
998
|
-
end
|
999
|
-
|
1000
|
-
if @env['REQUEST_METHOD'] == "POST"
|
1001
|
-
if @env.has_key?("CONTENT_TYPE") && @env['CONTENT_TYPE'] == "application/x-www-form-urlencoded" && @env.has_key?('CONTENT_LENGTH')
|
1002
|
-
unless @settings.has_key?("post seperator")
|
1003
|
-
post_args = $stdin.read(@env['CONTENT_LENGTH'].to_i).split(/[&;]/)
|
1004
|
-
else
|
1005
|
-
post_args = $stdin.read(@env['CONTENT_LENGTH'].to_i).split(@settings['post seperator'])
|
1006
|
-
end
|
1007
|
-
post_args.each do | arg |
|
1008
|
-
arg_key, arg_val = arg.split(/=/, 2)
|
1009
|
-
arg_key = Rweb::unescape(arg_key)
|
1010
|
-
arg_val = Rweb::unescape(arg_val)
|
1011
|
-
|
1012
|
-
# Parse names like name[0], name['text'] or name[]
|
1013
|
-
pattern = /^(.+)\[("[^\]]*"|'[^\]]*'|[0-9]*)\]$/
|
1014
|
-
keys = []
|
1015
|
-
while match = pattern.match(arg_key)
|
1016
|
-
arg_key = match[1]
|
1017
|
-
keys = [match[2]] + keys
|
1018
|
-
end
|
1019
|
-
keys = [arg_key] + keys
|
1020
|
-
|
1021
|
-
akt = @post
|
1022
|
-
last = nil
|
1023
|
-
lastkey = nil
|
1024
|
-
keys.each do |key|
|
1025
|
-
if key == ""
|
1026
|
-
# No key specified (like in "test[]"), so we use
|
1027
|
-
# the lowerst unused Integer as key
|
1028
|
-
key = 0
|
1029
|
-
while akt.has_key?(key)
|
1030
|
-
key += 1
|
1031
|
-
end
|
1032
|
-
elsif /^[0-9]*$/ =~ key
|
1033
|
-
# If the index is numerical convert it to an Integer
|
1034
|
-
key = key.to_i
|
1035
|
-
elsif key[0].chr == "'" || key[0].chr == '"'
|
1036
|
-
key = key[1, key.length() -2]
|
1037
|
-
end
|
1038
|
-
if !akt.has_key?(key) || !akt[key].class == Hash
|
1039
|
-
# create an empty Hash if there isn't already one
|
1040
|
-
akt[key] = {}
|
1041
|
-
end
|
1042
|
-
last = akt
|
1043
|
-
lastkey = key
|
1044
|
-
akt = akt[key]
|
1045
|
-
end
|
1046
|
-
last[lastkey] = arg_val
|
1047
|
-
end
|
1048
|
-
else
|
1049
|
-
# Maybe we should print a warning here?
|
1050
|
-
$stderr.print("Unidentified form data recived and discarded.")
|
1051
|
-
end
|
1052
|
-
end
|
1053
|
-
|
1054
|
-
if @env.has_key?("HTTP_COOKIE")
|
1055
|
-
cookie = @env['HTTP_COOKIE'].split(/; ?/)
|
1056
|
-
cookie.each do | c |
|
1057
|
-
cookie_key, cookie_val = c.split(/=/, 2)
|
1058
|
-
|
1059
|
-
@cookies [Rweb::unescape(cookie_key)] = Rweb::unescape(cookie_val)
|
1060
|
-
end
|
1061
|
-
end
|
1062
|
-
|
1063
|
-
if defined?(@env['HTTP_USER_AGENT'])
|
1064
|
-
@user_agent = @env['HTTP_USER_AGENT']
|
1065
|
-
else
|
1066
|
-
@user_agent = nil;
|
1067
|
-
end
|
1068
|
-
|
1069
|
-
if defined?(@env['REMOTE_ADDR'])
|
1070
|
-
@remote_addr = @env['REMOTE_ADDR']
|
1071
|
-
else
|
1072
|
-
@remote_addr = nil
|
1073
|
-
end
|
1074
|
-
# }}}
|
1075
|
-
end
|
1076
|
-
|
1077
|
-
# Prints a String to the client. If caching is enabled, the String will
|
1078
|
-
# buffered until the end of the out block ends.
|
1079
|
-
def print(str = "")
|
1080
|
-
# {{{
|
1081
|
-
unless @output_allowed
|
1082
|
-
raise "You just can write to output inside of a Rweb::out-block"
|
1083
|
-
end
|
1084
|
-
|
1085
|
-
if @settings["cache"]
|
1086
|
-
@buffer += [str.to_s]
|
1087
|
-
else
|
1088
|
-
unless @output_started
|
1089
|
-
sendHeaders
|
1090
|
-
end
|
1091
|
-
$stdout.print(str)
|
1092
|
-
end
|
1093
|
-
nil
|
1094
|
-
# }}}
|
1095
|
-
end
|
1096
|
-
|
1097
|
-
# Prints a String to the client and adds a line break at the end. Please
|
1098
|
-
# remember, that a line break is not visible in HTML, use the <br> HTML-Tag
|
1099
|
-
# for this. If caching is enabled, the String will buffered until the end
|
1100
|
-
# of the out block ends.
|
1101
|
-
def puts(str = "")
|
1102
|
-
# {{{
|
1103
|
-
self.print(str + "\n")
|
1104
|
-
# }}}
|
1105
|
-
end
|
1106
|
-
|
1107
|
-
# Alias to print.
|
1108
|
-
def write(str = "")
|
1109
|
-
# {{{
|
1110
|
-
self.print(str)
|
1111
|
-
# }}}
|
1112
|
-
end
|
1113
|
-
|
1114
|
-
# If caching is enabled, all cached data are send to the cliend and the
|
1115
|
-
# cache emptied.
|
1116
|
-
def flush
|
1117
|
-
# {{{
|
1118
|
-
unless @output_allowed
|
1119
|
-
raise "You can't use flush outside of a Rweb::out-block"
|
1120
|
-
end
|
1121
|
-
buffer = @buffer.join
|
1122
|
-
|
1123
|
-
unless @output_started
|
1124
|
-
sendHeaders
|
1125
|
-
end
|
1126
|
-
$stdout.print(buffer)
|
1127
|
-
|
1128
|
-
@buffer = []
|
1129
|
-
# }}}
|
1130
|
-
end
|
1131
|
-
|
1132
|
-
# Sends one or more header to the client. All headers are cached just
|
1133
|
-
# before body data are send to the client. If the same header are set
|
1134
|
-
# twice, only the last value is send.
|
1135
|
-
#
|
1136
|
-
# Example:
|
1137
|
-
# web.header("Last-Modified: Mon, 16 Feb 2004 20:15:41 GMT")
|
1138
|
-
# web.header("Location: http://www.ruby-lang.org")
|
1139
|
-
#
|
1140
|
-
# You can specify more than one header at the time by doing something like
|
1141
|
-
# this:
|
1142
|
-
# web.header("Content-Type: text/plain\nContent-Length: 383")
|
1143
|
-
# or
|
1144
|
-
# web.header(["Content-Type: text/plain", "Content-Length: 383"])
|
1145
|
-
def header(str)
|
1146
|
-
# {{{
|
1147
|
-
if @output_started
|
1148
|
-
raise "HTTP-Headers are already send. You can't change them after output has started!"
|
1149
|
-
end
|
1150
|
-
unless @output_allowed
|
1151
|
-
raise "You just can set headers inside of a Rweb::out-block"
|
1152
|
-
end
|
1153
|
-
if str.is_a?Array
|
1154
|
-
str.each do | value |
|
1155
|
-
self.header(value)
|
1156
|
-
end
|
1157
|
-
|
1158
|
-
elsif str.split(/\n/).length > 1
|
1159
|
-
str.split(/\n/).each do | value |
|
1160
|
-
self.header(value)
|
1161
|
-
end
|
1162
|
-
|
1163
|
-
elsif str.is_a? String
|
1164
|
-
str.gsub!(/\r/, "")
|
1165
|
-
|
1166
|
-
if (str =~ /^HTTP\/1\.[01] [0-9]{3} ?.*$/) == 0
|
1167
|
-
pattern = /^HTTP\/1.[01] ([0-9]{3}) ?(.*)$/
|
1168
|
-
|
1169
|
-
result = pattern.match(str)
|
1170
|
-
self.setstatus(result[0], result[1])
|
1171
|
-
elsif (str =~ /^status: [0-9]{3} ?.*$/i) == 0
|
1172
|
-
pattern = /^status: ([0-9]{3}) ?(.*)$/i
|
1173
|
-
|
1174
|
-
result = pattern.match(str)
|
1175
|
-
self.setstatus(result[0], result[1])
|
1176
|
-
else
|
1177
|
-
a = str.split(/: ?/, 2)
|
1178
|
-
|
1179
|
-
@header[a[0].downcase] = a[1]
|
1180
|
-
end
|
1181
|
-
end
|
1182
|
-
# }}}
|
1183
|
-
end
|
1184
|
-
|
1185
|
-
# Changes the status of this page. There are several codes like "200 OK",
|
1186
|
-
# "302 Found", "404 Not Found" or "500 Internal Server Error". A list of
|
1187
|
-
# all codes is available at
|
1188
|
-
# http://www.w3.org/Protocols/rfc2616/rfc2616-sec10.html#sec10
|
1189
|
-
#
|
1190
|
-
# You can just send the code number, the reason phrase will be added
|
1191
|
-
# automaticly with the recommendations from the w3c if not specified. If
|
1192
|
-
# you set the status twice or more, only the last status will be send.
|
1193
|
-
# Examples:
|
1194
|
-
# web.status("401 Unauthorized")
|
1195
|
-
# web.status("410 Sad but true, this lonely page is gone :(")
|
1196
|
-
# web.status(206)
|
1197
|
-
# web.status("400")
|
1198
|
-
#
|
1199
|
-
# The default status is "200 OK". If a "Location" header is set, the
|
1200
|
-
# default status is "302 Found".
|
1201
|
-
def status(str)
|
1202
|
-
# {{{
|
1203
|
-
if @output_started
|
1204
|
-
raise "HTTP-Headers are already send. You can't change them after output has started!"
|
1205
|
-
end
|
1206
|
-
unless @output_allowed
|
1207
|
-
raise "You just can set headers inside of a Rweb::out-block"
|
1208
|
-
end
|
1209
|
-
if str.is_a?Integer
|
1210
|
-
@status = str
|
1211
|
-
elsif str.is_a?String
|
1212
|
-
p1 = /^([0-9]{3}) ?(.*)$/
|
1213
|
-
p2 = /^HTTP\/1\.[01] ([0-9]{3}) ?(.*)$/
|
1214
|
-
p3 = /^status: ([0-9]{3}) ?(.*)$/i
|
1215
|
-
|
1216
|
-
if (a = p1.match(str)) == nil
|
1217
|
-
if (a = p2.match(str)) == nil
|
1218
|
-
if (a = p3.match(str)) == nil
|
1219
|
-
raise ArgumentError, "Invalid argument", caller
|
1220
|
-
end
|
1221
|
-
end
|
1222
|
-
end
|
1223
|
-
@status = a[1].to_i
|
1224
|
-
if a[2] != ""
|
1225
|
-
@reasonPhrase = a[2]
|
1226
|
-
else
|
1227
|
-
@reasonPhrase = getReasonPhrase(@status)
|
1228
|
-
end
|
1229
|
-
else
|
1230
|
-
raise ArgumentError, "Argument of setstatus must be integer or string", caller
|
1231
|
-
end
|
1232
|
-
# }}}
|
1233
|
-
end
|
1234
|
-
|
1235
|
-
# Handles the output of your content and rescues all exceptions. Send all
|
1236
|
-
# data in the block to this method. For example:
|
1237
|
-
# web.out do
|
1238
|
-
# web.header("Content-Type: text/plain")
|
1239
|
-
# web.puts("Hello, plain world!")
|
1240
|
-
# end
|
1241
|
-
def out
|
1242
|
-
# {{{
|
1243
|
-
@output_allowed = true
|
1244
|
-
@buffer = []; # We use an array as buffer, because it's more performant :)
|
1245
|
-
|
1246
|
-
begin
|
1247
|
-
yield
|
1248
|
-
rescue Exception => exception
|
1249
|
-
$stderr.puts "Ruby exception rescued (#{exception.class}): #{exception.message}"
|
1250
|
-
$stderr.puts exception.backtrace.join("\n")
|
1251
|
-
|
1252
|
-
unless @output_started
|
1253
|
-
self.setstatus(500)
|
1254
|
-
@header = {}
|
1255
|
-
end
|
1256
|
-
|
1257
|
-
unless (@settings.has_key?("hide errors") and @settings["hide errors"] == true)
|
1258
|
-
unless @output_started
|
1259
|
-
self.header("Content-Type: text/html")
|
1260
|
-
self.puts "<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Strict//EN\" \"http://www.w3.org/TR/html4/strict.dtd\">"
|
1261
|
-
self.puts "<html>"
|
1262
|
-
self.puts "<head>"
|
1263
|
-
self.puts "<title>500 Internal Server Error</title>"
|
1264
|
-
self.puts "</head>"
|
1265
|
-
self.puts "<body>"
|
1266
|
-
end
|
1267
|
-
if @header.has_key?("content-type") and (@header["content-type"] =~ /^text\/html/i) == 0
|
1268
|
-
self.puts "<h1>Internal Server Error</h1>"
|
1269
|
-
self.puts "<p>The server encountered an exception and was unable to complete your request.</p>"
|
1270
|
-
self.puts "<p>The exception has provided the following information:</p>"
|
1271
|
-
self.puts "<pre style=\"background: #FFCCCC; border: black solid 2px; margin-left: 2cm; margin-right: 2cm; padding: 2mm;\"><b>#{exception.class}</b>: #{exception.message} <b>on</b>"
|
1272
|
-
self.puts
|
1273
|
-
self.puts "#{exception.backtrace.join("\n")}</pre>"
|
1274
|
-
self.puts "</body>"
|
1275
|
-
self.puts "</html>"
|
1276
|
-
else
|
1277
|
-
self.puts "The server encountered an exception and was unable to complete your request"
|
1278
|
-
self.puts "The exception has provided the following information:"
|
1279
|
-
self.puts "#{exception.class}: #{exception.message}"
|
1280
|
-
self.puts
|
1281
|
-
self.puts exception.backtrace.join("\n")
|
1282
|
-
end
|
1283
|
-
end
|
1284
|
-
end
|
1285
|
-
|
1286
|
-
if @settings["cache"]
|
1287
|
-
buffer = @buffer.join
|
1288
|
-
|
1289
|
-
unless @output_started
|
1290
|
-
unless @header.has_key?("content-length")
|
1291
|
-
self.header("content-length: #{buffer.length}")
|
1292
|
-
end
|
1293
|
-
|
1294
|
-
sendHeaders
|
1295
|
-
end
|
1296
|
-
$stdout.print(buffer)
|
1297
|
-
elsif !@output_started
|
1298
|
-
sendHeaders
|
1299
|
-
end
|
1300
|
-
@output_allowed = false;
|
1301
|
-
# }}}
|
1302
|
-
end
|
1303
|
-
|
1304
|
-
# Decodes URL encoded data, %20 for example stands for a space.
|
1305
|
-
def Rweb.unescape(str)
|
1306
|
-
# {{{
|
1307
|
-
if defined? str and str.is_a? String
|
1308
|
-
str.gsub!(/\+/, " ")
|
1309
|
-
str.gsub(/%.{2}/) do | s |
|
1310
|
-
s[1,2].hex.chr
|
1311
|
-
end
|
1312
|
-
end
|
1313
|
-
# }}}
|
1314
|
-
end
|
1315
|
-
|
1316
|
-
protected
|
1317
|
-
def sendHeaders
|
1318
|
-
# {{{
|
1319
|
-
|
1320
|
-
Cookie.disallow # no more cookies can be set or modified
|
1321
|
-
if !(@settings.has_key?("silent") and @settings["silent"] == true) and !@header.has_key?("x-powered-by")
|
1322
|
-
if @mod_ruby
|
1323
|
-
header("x-powered-by: #{RWEB} (Ruby/#{RUBY_VERSION}, #{MOD_RUBY})");
|
1324
|
-
else
|
1325
|
-
header("x-powered-by: #{RWEB} (Ruby/#{RUBY_VERSION})");
|
1326
|
-
end
|
1327
|
-
end
|
1328
|
-
|
1329
|
-
if @output_method == "ph"
|
1330
|
-
if ((@status == nil or @status == 200) and !@header.has_key?("content-type") and !@header.has_key?("location"))
|
1331
|
-
header("content-type: text/html")
|
1332
|
-
end
|
1333
|
-
|
1334
|
-
if @status != nil
|
1335
|
-
$stdout.print "Status: #{@status} #{@reasonPhrase}\r\n"
|
1336
|
-
end
|
1337
|
-
|
1338
|
-
@header.each do |key, value|
|
1339
|
-
key = key *1 # "unfreeze" key :)
|
1340
|
-
key[0] = key[0,1].upcase![0]
|
1341
|
-
|
1342
|
-
key = key.gsub(/-[a-z]/) do |char|
|
1343
|
-
"-" + char[1,1].upcase
|
1344
|
-
end
|
1345
|
-
|
1346
|
-
$stdout.print "#{key}: #{value}\r\n"
|
1347
|
-
end
|
1348
|
-
cookies = Cookie.getHttpHeader # Get all cookies as an HTTP Header
|
1349
|
-
if cookies
|
1350
|
-
$stdout.print cookies
|
1351
|
-
end
|
1352
|
-
|
1353
|
-
$stdout.print "\r\n"
|
1354
|
-
|
1355
|
-
elsif @output_method == "nph"
|
1356
|
-
elsif @output_method == "mod_ruby"
|
1357
|
-
r = Apache.request
|
1358
|
-
|
1359
|
-
if ((@status == nil or @status == 200) and !@header.has_key?("content-type") and !@header.has_key?("location"))
|
1360
|
-
header("text/html")
|
1361
|
-
end
|
1362
|
-
|
1363
|
-
if @status != nil
|
1364
|
-
r.status_line = "#{@status} #{@reasonPhrase}"
|
1365
|
-
end
|
1366
|
-
|
1367
|
-
r.send_http_header
|
1368
|
-
@header.each do |key, value|
|
1369
|
-
key = key *1 # "unfreeze" key :)
|
1370
|
-
|
1371
|
-
key[0] = key[0,1].upcase![0]
|
1372
|
-
key = key.gsub(/-[a-z]/) do |char|
|
1373
|
-
"-" + char[1,1].upcase
|
1374
|
-
end
|
1375
|
-
puts "#{key}: #{value.class}"
|
1376
|
-
#r.headers_out[key] = value
|
1377
|
-
end
|
1378
|
-
end
|
1379
|
-
@output_started = true
|
1380
|
-
# }}}
|
1381
|
-
end
|
1382
|
-
|
1383
|
-
def getReasonPhrase (status)
|
1384
|
-
# {{{
|
1385
|
-
if status == 100
|
1386
|
-
"Continue"
|
1387
|
-
elsif status == 101
|
1388
|
-
"Switching Protocols"
|
1389
|
-
elsif status == 200
|
1390
|
-
"OK"
|
1391
|
-
elsif status == 201
|
1392
|
-
"Created"
|
1393
|
-
elsif status == 202
|
1394
|
-
"Accepted"
|
1395
|
-
elsif status == 203
|
1396
|
-
"Non-Authoritative Information"
|
1397
|
-
elsif status == 204
|
1398
|
-
"No Content"
|
1399
|
-
elsif status == 205
|
1400
|
-
"Reset Content"
|
1401
|
-
elsif status == 206
|
1402
|
-
"Partial Content"
|
1403
|
-
elsif status == 300
|
1404
|
-
"Multiple Choices"
|
1405
|
-
elsif status == 301
|
1406
|
-
"Moved Permanently"
|
1407
|
-
elsif status == 302
|
1408
|
-
"Found"
|
1409
|
-
elsif status == 303
|
1410
|
-
"See Other"
|
1411
|
-
elsif status == 304
|
1412
|
-
"Not Modified"
|
1413
|
-
elsif status == 305
|
1414
|
-
"Use Proxy"
|
1415
|
-
elsif status == 307
|
1416
|
-
"Temporary Redirect"
|
1417
|
-
elsif status == 400
|
1418
|
-
"Bad Request"
|
1419
|
-
elsif status == 401
|
1420
|
-
"Unauthorized"
|
1421
|
-
elsif status == 402
|
1422
|
-
"Payment Required"
|
1423
|
-
elsif status == 403
|
1424
|
-
"Forbidden"
|
1425
|
-
elsif status == 404
|
1426
|
-
"Not Found"
|
1427
|
-
elsif status == 405
|
1428
|
-
"Method Not Allowed"
|
1429
|
-
elsif status == 406
|
1430
|
-
"Not Acceptable"
|
1431
|
-
elsif status == 407
|
1432
|
-
"Proxy Authentication Required"
|
1433
|
-
elsif status == 408
|
1434
|
-
"Request Time-out"
|
1435
|
-
elsif status == 409
|
1436
|
-
"Conflict"
|
1437
|
-
elsif status == 410
|
1438
|
-
"Gone"
|
1439
|
-
elsif status == 411
|
1440
|
-
"Length Required"
|
1441
|
-
elsif status == 412
|
1442
|
-
"Precondition Failed"
|
1443
|
-
elsif status == 413
|
1444
|
-
"Request Entity Too Large"
|
1445
|
-
elsif status == 414
|
1446
|
-
"Request-URI Too Large"
|
1447
|
-
elsif status == 415
|
1448
|
-
"Unsupported Media Type"
|
1449
|
-
elsif status == 416
|
1450
|
-
"Requested range not satisfiable"
|
1451
|
-
elsif status == 417
|
1452
|
-
"Expectation Failed"
|
1453
|
-
elsif status == 500
|
1454
|
-
"Internal Server Error"
|
1455
|
-
elsif status == 501
|
1456
|
-
"Not Implemented"
|
1457
|
-
elsif status == 502
|
1458
|
-
"Bad Gateway"
|
1459
|
-
elsif status == 503
|
1460
|
-
"Service Unavailable"
|
1461
|
-
elsif status == 504
|
1462
|
-
"Gateway Time-out"
|
1463
|
-
elsif status == 505
|
1464
|
-
"HTTP Version not supported"
|
1465
|
-
else
|
1466
|
-
raise "Unknown Statuscode. See http://www.w3.org/Protocols/rfc2616/rfc2616-sec6.html#sec6.1 for more information."
|
1467
|
-
end
|
1468
|
-
# }}}
|
1469
|
-
end
|
1470
|
-
end
|
1471
|
-
|
1472
|
-
class Cookie
|
1473
|
-
attr_reader :name, :value, :maxage, :path, :domain, :secure, :comment
|
1474
|
-
|
1475
|
-
# Sets a cookie. Please see below for details of the attributes.
|
1476
|
-
def initialize (name, value = nil, maxage = nil, path = nil, domain = nil, secure = false)
|
1477
|
-
# {{{
|
1478
|
-
# HTTP headers (Cookies are a HTTP header) can only set, while no content
|
1479
|
-
# is send. So an exception will be raised, when @@allowed is set to false
|
1480
|
-
# and a new cookie has set.
|
1481
|
-
unless defined?(@@allowed)
|
1482
|
-
@@allowed = true
|
1483
|
-
end
|
1484
|
-
unless @@allowed
|
1485
|
-
raise "You can't set cookies after the HTTP headers are send."
|
1486
|
-
end
|
1487
|
-
|
1488
|
-
unless defined?(@@list)
|
1489
|
-
@@list = []
|
1490
|
-
end
|
1491
|
-
@@list += [self]
|
1492
|
-
|
1493
|
-
unless defined?(@@type)
|
1494
|
-
@@type = "netscape"
|
1495
|
-
end
|
1496
|
-
|
1497
|
-
unless name.class == String
|
1498
|
-
raise TypeError, "The name of a cookie must be a string", caller
|
1499
|
-
end
|
1500
|
-
if value.class.superclass == Integer || value.class == Float
|
1501
|
-
value = value.to_s
|
1502
|
-
elsif value.class != String && value != nil
|
1503
|
-
raise TypeError, "The value of a cookie must be a string, integer, float or nil", caller
|
1504
|
-
end
|
1505
|
-
if maxage.class == Time
|
1506
|
-
maxage = maxage - Time.now
|
1507
|
-
elsif !maxage.class.superclass == Integer || !maxage == nil
|
1508
|
-
raise TypeError, "The maxage date of a cookie must be an Integer or Time object or nil.", caller
|
1509
|
-
end
|
1510
|
-
unless path.class == String || path == nil
|
1511
|
-
raise TypeError, "The path of a cookie must be nil or a string", caller
|
1512
|
-
end
|
1513
|
-
unless domain.class == String || domain == nil
|
1514
|
-
raise TypeError, "The value of a cookie must be nil or a string", caller
|
1515
|
-
end
|
1516
|
-
unless secure == true || secure == false
|
1517
|
-
raise TypeError, "The secure field of a cookie must be true or false", caller
|
1518
|
-
end
|
1519
|
-
|
1520
|
-
@name, @value, @maxage, @path, @domain, @secure = name, value, maxage, path, domain, secure
|
1521
|
-
@comment = nil
|
1522
|
-
# }}}
|
1523
|
-
end
|
1524
|
-
|
1525
|
-
# Modifies the value of this cookie. The information you want to store. If the
|
1526
|
-
# value is nil, the cookie will be deleted by the client.
|
1527
|
-
#
|
1528
|
-
# This attribute can be a String, Integer or Float object or nil.
|
1529
|
-
def value=(value)
|
1530
|
-
# {{{
|
1531
|
-
if value.class.superclass == Integer || value.class == Float
|
1532
|
-
value = value.to_s
|
1533
|
-
elsif value.class != String && value != nil
|
1534
|
-
raise TypeError, "The value of a cookie must be a string, integer, float or nil", caller
|
1535
|
-
end
|
1536
|
-
@value = value
|
1537
|
-
# }}}
|
1538
|
-
end
|
1539
|
-
|
1540
|
-
# Modifies the maxage of this cookie. This attribute defines the lifetime of
|
1541
|
-
# the cookie, in seconds. A value of 0 means the cookie should be discarded
|
1542
|
-
# imediatly. If it set to nil, the cookie will be deleted when the browser
|
1543
|
-
# will be closed.
|
1544
|
-
#
|
1545
|
-
# Attention: This is different from other implementations like PHP, where you
|
1546
|
-
# gives the seconds since 1/1/1970 0:00:00 GMT.
|
1547
|
-
#
|
1548
|
-
# This attribute must be an Integer or Time object or nil.
|
1549
|
-
def maxage=(maxage)
|
1550
|
-
# {{{
|
1551
|
-
if maxage.class == Time
|
1552
|
-
maxage = maxage - Time.now
|
1553
|
-
elsif maxage.class.superclass == Integer || !maxage == nil
|
1554
|
-
raise TypeError, "The maxage of a cookie must be an Interger or Time object or nil.", caller
|
1555
|
-
end
|
1556
|
-
@maxage = maxage
|
1557
|
-
# }}}
|
1558
|
-
end
|
1559
|
-
|
1560
|
-
# Modifies the path value of this cookie. The client will send this cookie
|
1561
|
-
# only, if the requested document is this directory or a subdirectory of it.
|
1562
|
-
#
|
1563
|
-
# The value of the attribute must be a String object or nil.
|
1564
|
-
def path=(path)
|
1565
|
-
# {{{
|
1566
|
-
unless path.class == String || path == nil
|
1567
|
-
raise TypeError, "The path of a cookie must be nil or a string", caller
|
1568
|
-
end
|
1569
|
-
@path = path
|
1570
|
-
# }}}
|
1571
|
-
end
|
1572
|
-
|
1573
|
-
# Modifies the domain value of this cookie. The client will send this cookie
|
1574
|
-
# only if it's connected with this domain (or a subdomain, if the first
|
1575
|
-
# character is a dot like in ".ruby-lang.org")
|
1576
|
-
#
|
1577
|
-
# The value of this attribute must be a String or nil.
|
1578
|
-
def domain=(domain)
|
1579
|
-
# {{{
|
1580
|
-
unless domain.class == String || domain == nil
|
1581
|
-
raise TypeError, "The domain of a cookie must be a String or nil.", caller
|
1582
|
-
end
|
1583
|
-
@domain = domain
|
1584
|
-
# }}}
|
1585
|
-
end
|
1586
|
-
|
1587
|
-
# Modifies the secure flag of this cookie. If it's true, the client will only
|
1588
|
-
# send this cookie if it is secured connected with us.
|
1589
|
-
#
|
1590
|
-
# The value od this attribute has to be true or false.
|
1591
|
-
def secure=(secure)
|
1592
|
-
# {{{
|
1593
|
-
unless secure == true || secure == false
|
1594
|
-
raise TypeError, "The secure field of a cookie must be true or false", caller
|
1595
|
-
end
|
1596
|
-
@secure = secure
|
1597
|
-
# }}}
|
1598
|
-
end
|
1599
|
-
|
1600
|
-
# Modifies the comment value of this cookie. The comment won't be send, if
|
1601
|
-
# type is "netscape".
|
1602
|
-
def comment=(comment)
|
1603
|
-
# {{{
|
1604
|
-
unless comment.class == String || comment == nil
|
1605
|
-
raise TypeError, "The comment of a cookie must be a string or nil", caller
|
1606
|
-
end
|
1607
|
-
@comment = comment
|
1608
|
-
# }}}
|
1609
|
-
end
|
1610
|
-
|
1611
|
-
# Changes the type of all cookies.
|
1612
|
-
# Allowed values are RFC2109 and netscape (default).
|
1613
|
-
def Cookie.type=(type)
|
1614
|
-
# {{{
|
1615
|
-
unless @@allowed
|
1616
|
-
raise "The cookies are allready send, so you can't change the type anymore."
|
1617
|
-
end
|
1618
|
-
unless type.downcase == "rfc2109" && type.downcase == "netscape"
|
1619
|
-
raise "The type of the cookies must be \"RFC2109\" or \"netscape\"."
|
1620
|
-
end
|
1621
|
-
@@type = type;
|
1622
|
-
# }}}
|
1623
|
-
end
|
1624
|
-
|
1625
|
-
# After sending this message, no cookies can be set or modified. Use it, when
|
1626
|
-
# HTTP-Headers are send. Rweb does this for you.
|
1627
|
-
def Cookie.disallow
|
1628
|
-
# {{{
|
1629
|
-
@@allowed = false
|
1630
|
-
true
|
1631
|
-
# }}}
|
1632
|
-
end
|
1633
|
-
|
1634
|
-
# Returns a HTTP header (type String) with all cookies. Rweb does this for
|
1635
|
-
# you.
|
1636
|
-
def Cookie.getHttpHeader
|
1637
|
-
# {{{
|
1638
|
-
if defined?(@@list)
|
1639
|
-
if @@type == "netscape"
|
1640
|
-
str = ""
|
1641
|
-
@@list.each do |cookie|
|
1642
|
-
if cookie.value == nil
|
1643
|
-
cookie.maxage = 0
|
1644
|
-
cookie.value = ""
|
1645
|
-
end
|
1646
|
-
# TODO: Name and value should be escaped!
|
1647
|
-
str += "Set-Cookie: #{cookie.name}=#{cookie.value}"
|
1648
|
-
unless cookie.maxage == nil
|
1649
|
-
expire = Time.now + cookie.maxage
|
1650
|
-
expire.gmtime
|
1651
|
-
str += "; Expire=#{expire.strftime("%a, %d-%b-%Y %H:%M:%S %Z")}"
|
1652
|
-
end
|
1653
|
-
unless cookie.domain == nil
|
1654
|
-
str += "; Domain=#{cookie.domain}"
|
1655
|
-
end
|
1656
|
-
unless cookie.path == nil
|
1657
|
-
str += "; Path=#{cookie.path}"
|
1658
|
-
end
|
1659
|
-
if cookie.secure
|
1660
|
-
str += "; Secure"
|
1661
|
-
end
|
1662
|
-
str += "\r\n"
|
1663
|
-
end
|
1664
|
-
return str
|
1665
|
-
else # type == "RFC2109"
|
1666
|
-
str = "Set-Cookie: "
|
1667
|
-
comma = false;
|
1668
|
-
|
1669
|
-
@@list.each do |cookie|
|
1670
|
-
if cookie.value == nil
|
1671
|
-
cookie.maxage = 0
|
1672
|
-
cookie.value = ""
|
1673
|
-
end
|
1674
|
-
if comma
|
1675
|
-
str += ","
|
1676
|
-
end
|
1677
|
-
comma = true
|
1678
|
-
|
1679
|
-
str += "#{cookie.name}=\"#{cookie.value}\""
|
1680
|
-
unless cookie.maxage == nil
|
1681
|
-
str += "; Max-Age=\"#{cookie.maxage}\""
|
1682
|
-
end
|
1683
|
-
unless cookie.domain == nil
|
1684
|
-
str += "; Domain=\"#{cookie.domain}\""
|
1685
|
-
end
|
1686
|
-
unless cookie.path == nil
|
1687
|
-
str += "; Path=\"#{cookie.path}\""
|
1688
|
-
end
|
1689
|
-
if cookie.secure
|
1690
|
-
str += "; Secure"
|
1691
|
-
end
|
1692
|
-
unless cookie.comment == nil
|
1693
|
-
str += "; Comment=\"#{cookie.comment}\""
|
1694
|
-
end
|
1695
|
-
str += "; Version=\"1\""
|
1696
|
-
end
|
1697
|
-
str
|
1698
|
-
end
|
1699
|
-
else
|
1700
|
-
false
|
1701
|
-
end
|
1702
|
-
# }}}
|
1703
|
-
end
|
1704
|
-
end
|
1705
|
-
|
1706
|
-
require 'strscan'
|
1707
|
-
|
1708
|
-
module BBCode
|
1709
|
-
DEBUG = true
|
1710
|
-
|
1711
|
-
use 'encoder', 'tags', 'tagstack', 'smileys'
|
1712
|
-
|
1713
|
-
=begin
|
1714
|
-
The Parser class takes care of the encoding.
|
1715
|
-
It scans the given BBCode (as plain text), finds tags
|
1716
|
-
and smilies and also makes links of urls in text.
|
1717
|
-
|
1718
|
-
Normal text is send directly to the encoder.
|
1719
|
-
|
1720
|
-
If a tag was found, an instance of a Tag subclass is created
|
1721
|
-
to handle the case.
|
1722
|
-
|
1723
|
-
The @tagstack manages tag nesting and ensures valid HTML.
|
1724
|
-
=end
|
1725
|
-
|
1726
|
-
class Parser
|
1727
|
-
class Attribute
|
1728
|
-
# flatten and use only one empty_arg
|
1729
|
-
def self.create attr
|
1730
|
-
attr = flatten attr
|
1731
|
-
return @@empty_attr if attr.empty?
|
1732
|
-
new attr
|
1733
|
-
end
|
1734
|
-
|
1735
|
-
private_class_method :new
|
1736
|
-
|
1737
|
-
# remove leading and trailing whitespace; concat lines
|
1738
|
-
def self.flatten attr
|
1739
|
-
attr.strip.gsub(/\n/, ' ')
|
1740
|
-
# -> ^ and $ can only match at begin and end now
|
1741
|
-
end
|
1742
|
-
|
1743
|
-
ATTRIBUTE_SCAN = /
|
1744
|
-
(?!$) # don't match at end
|
1745
|
-
\s*
|
1746
|
-
( # $1 = key
|
1747
|
-
[^=\s\]"\\]*
|
1748
|
-
(?:
|
1749
|
-
(?: \\. | "[^"\\]*(?:\\.[^"\\]*)*"? )
|
1750
|
-
[^=\s\]"\\]*
|
1751
|
-
)*
|
1752
|
-
)
|
1753
|
-
(?:
|
1754
|
-
=
|
1755
|
-
( # $2 = value
|
1756
|
-
[^\s\]"\\]*
|
1757
|
-
(?:
|
1758
|
-
(?: \\. | "[^"\\]*(?:\\.[^"\\]*)*"? )
|
1759
|
-
[^\s\]"\\]*
|
1760
|
-
)*
|
1761
|
-
)?
|
1762
|
-
)?
|
1763
|
-
\s*
|
1764
|
-
/x
|
1765
|
-
|
1766
|
-
def self.parse source
|
1767
|
-
source = source.dup
|
1768
|
-
# empty_tag: the tag looks like [... /]
|
1769
|
-
# slice!: this deletes the \s*/] at the end
|
1770
|
-
# \s+ because [url=http://rubybb.org/forum/] is NOT an empty tag.
|
1771
|
-
# In RubyBBCode, you can use [url=http://rubybb.org/forum/ /], and this has to be
|
1772
|
-
# interpreted correctly.
|
1773
|
-
empty_tag = source.sub!(/^:/, '=') or source.slice!(/\/$/)
|
1774
|
-
debug 'PARSE: ' + source.inspect + ' => ' + empty_tag.inspect
|
1775
|
-
#-> we have now an attr that's EITHER empty OR begins and ends with non-whitespace.
|
1776
|
-
|
1777
|
-
attr = Hash.new
|
1778
|
-
attr[:flags] = []
|
1779
|
-
source.scan(ATTRIBUTE_SCAN) { |key, value|
|
1780
|
-
if not value
|
1781
|
-
attr[:flags] << unescape(key)
|
1782
|
-
else
|
1783
|
-
next if value.empty? and key.empty?
|
1784
|
-
attr[unescape(key)] = unescape(value)
|
1785
|
-
end
|
1786
|
-
}
|
1787
|
-
debug attr.inspect
|
1788
|
-
|
1789
|
-
return empty_tag, attr
|
1790
|
-
end
|
1791
|
-
|
1792
|
-
def self.unescape_char esc
|
1793
|
-
esc[1]
|
1794
|
-
end
|
1795
|
-
|
1796
|
-
def self.unquote qt
|
1797
|
-
qt[1..-1].chomp('"').gsub(/\\./) { |esc| unescape_char esc }
|
1798
|
-
end
|
1799
|
-
|
1800
|
-
def self.unescape str
|
1801
|
-
str.gsub(/ (\\.) | (" [^"\\]* (?:\\.[^"\\]*)* "?) /x) {
|
1802
|
-
if $1
|
1803
|
-
unescape_char $1
|
1804
|
-
else
|
1805
|
-
unquote $2
|
1806
|
-
end
|
1807
|
-
}
|
1808
|
-
end
|
1809
|
-
|
1810
|
-
include Enumerable
|
1811
|
-
def each &block
|
1812
|
-
@args.each(&block)
|
1813
|
-
end
|
1814
|
-
|
1815
|
-
attr_reader :source, :args, :value
|
1816
|
-
|
1817
|
-
def initialize source
|
1818
|
-
@source = source
|
1819
|
-
debug 'Attribute#new(%p)' % source
|
1820
|
-
@empty_tag, @attr = Attribute.parse source
|
1821
|
-
@value = @attr[''].to_s
|
1822
|
-
end
|
1823
|
-
|
1824
|
-
def empty?
|
1825
|
-
self == @@empty_attr
|
1826
|
-
end
|
1827
|
-
|
1828
|
-
def empty_tag?
|
1829
|
-
@empty_tag
|
1830
|
-
end
|
1831
|
-
|
1832
|
-
def [] *keys
|
1833
|
-
res = @attr[*keys]
|
1834
|
-
end
|
1835
|
-
|
1836
|
-
def flags
|
1837
|
-
attr[:flags]
|
1838
|
-
end
|
1839
|
-
|
1840
|
-
def to_s
|
1841
|
-
@attr
|
1842
|
-
end
|
1843
|
-
|
1844
|
-
def inspect
|
1845
|
-
'ATTR[' + @attr.inspect + (@empty_tag ? ' | empty tag' : '') + ']'
|
1846
|
-
end
|
1847
|
-
end
|
1848
|
-
class Attribute
|
1849
|
-
@@empty_attr = new ''
|
1850
|
-
end
|
1851
|
-
end
|
1852
|
-
|