The new signup screen shows more feedback and requires to write the password twice.
Pull-Request: #2154
Reviewed-by: Jean Privat <jean@pryen.org>
project ( http://nitlanguage.org ).
Files: *
-Copyright: 2004-2015 Jean Privat <jean@pryen.org>
+Copyright: 2004-2016 Jean Privat <jean@pryen.org>
2006-2008 Floréal Morandat <morandat@lirmm.fr>
2009 Julien Chevalier <chevjulien@gmail.com>
2009-2011 Jean-Sebastien Gelinas <calestar@gmail.com>
- 2009-2015 Alexis Laferrière <alexis.laf@xymus.net>
+ 2009-2016 Alexis Laferrière <alexis.laf@xymus.net>
2011 Matthieu Auger <matthieu.auger@gmail.com>
- 2011-2015 Alexandre Terrasa <alexandre@moz-code.org>
+ 2011-2016 Alexandre Terrasa <alexandre@moz-code.org>
2012 Alexandre Pennetier <alexandre.pennetier@me.com>
- 2013-2015 Lucas Bajolet <r4pass@hotmail.com>
+ 2013-2016 Lucas Bajolet <r4pass@hotmail.com>
2013 Stefan Lage <lagestfan@gmail.com>
2013 Nathan Heu <heu.nathan@courrier.uqam.ca>
2013 Matthieu Lucas <lucasmatthieu@gmail.com>
- 2014-2015 Romain Chanoir <romain.chanoir@viacesi.fr>
- 2014 Frédéric Vachon <fredvac@gmail.com>
+ 2014-2016 Romain Chanoir <romain.chanoir@viacesi.fr>
+ 2014-2015 Frédéric Vachon <fredvac@gmail.com>
2014 Johan Kayser <johan.kayser@viacesi.fr>
2014-2015 Julien Pagès <julien.projet@gmail.com>
2014 Geoffrey Hecht <geoffrey.hecht@gmail.com>
- 2014 Jean-Christophe Beaupré <jcbrinfo@users.noreply.github.com>
+ 2014-2016 Jean-Christophe Beaupré <jcbrinfo@users.noreply.github.com>
2015 Arthur Delamare <arthur.delamare@viacesi.fr>
+ 2015-2016 Mehdi Ait Younes <overpex@gmail.com>
+ 2015 Renata Carvalho <renatawm@gmail.com>
+ 2015 Simon Zeni <simonzeni@gmail.com>
+ 2015 Anis Boubaker <anis@boubaker.ca>
+ 2015 Istvan SZALAI <szalai972@gmail.com>
+ 2015 Hervé Matysiak <herve.matysiak@viacesi.fr>
+ 2015 Jean-Philippe Caissy <jean-philippe.caissy@shopify.com>
+ 2015 Alexandre Blondin Massé <alexandre.blondin.masse@gmail.com>
+ 2015-2016 Guilherme Mansur <guilhermerpmansur@gmail.com>
+ 2016 Tony Gaetani <tony.gaetani@gmail.com>
License: Apache 2.0 (see LICENSE)
Comment: The main license of the work, except for the following exceptions
Files: lib/*
clib/*
share/nitdoc/*
-Copyright: 2004-2015 Jean Privat <jean@pryen.org>
+Copyright: 2004-2016 Jean Privat <jean@pryen.org>
2006-2008 Floréal Morandat <morandat@lirmm.fr>
2009-2011 Jean-Sebastien Gelinas <calestar@gmail.com>
- 2009-2015 Alexis Laferrière <alexis.laf@xymus.net>
+ 2009-2016 Alexis Laferrière <alexis.laf@xymus.net>
2009 Julien Chevalier <chevjulien@gmail.com>
- 2011-2015 Alexandre Terrasa <alexandre@moz-concept.com>
+ 2011-2016 Alexandre Terrasa <alexandre@moz-concept.com>
2012 Alexandre Pennetier <alexandre.pennetier@me.com>
- 2013-2015 Lucas Bajolet <r4pass@hotmail.com>
+ 2013-2016 Lucas Bajolet <r4pass@hotmail.com>
2013 Nathan Heu <heu.nathan@courrier.uqam.ca>
2013 Matthieu Lucas <lucasmatthieu@gmail.com>
2013 Stefan Lage <lagestfan@gmail.com>
2014 Maxime Leroy <maxime.leroy76@gmail.com>
2014 Johann Dubois <johann.dubois@outlook.com>
2014-2015 Jean-Christophe Beaupré <jcbrinfo@users.noreply.github.com>
- 2014 Alexandre Blondin Massé <alexandre.blondin.masse@gmail.com>
+ 2014-2015 Alexandre Blondin Massé <alexandre.blondin.masse@gmail.com>
+ 2015 Mehdi Ait Younes <overpex@gmail.com>
+ 2015 Budi Kurniawan <budi2020@gmail.com>
+ 2015-2016 Philippe Pepos Petitclerc <ppeposp@gmail.com>
+ 2015-2016 Guilherme Mansur <guilhermerpmansur@gmail.com>
Licence: BSD 2 (see LICENSE-BSD)
Comment: Use of libraries and resources is basically unrestricted. We hold the copyright
on the compiler and the tools but not on the programs made by the users.
* gcc http://gcc.gnu.org/ (or a compatible C compiler)
* pkg-config http://www.freedesktop.org/wiki/Software/pkg-config/
* ccache http://ccache.samba.org/ to improve recompilation
- * libgc-dev http://www.hpl.hp.com/personal/Hans_Boehm/gc/
+ * libgc-dev http://hboehm.info/gc/
* graphviz http://www.graphviz.org/ to enable graphs with the nitdoc tool
* libunwind http://nongnu.org/libunwind
game.save
end
- # Maximum wanted frame per second
- var max_fps = 30
-
- # clock used to track FPS
- private var clock = new Clock
-
redef fun frame_core(display)
do
game.step
game.draw(display)
- var dt = clock.lapse
- var target_dt = 1000000000 / max_fps
- if dt.sec == 0 and dt.nanosec < target_dt then
- var sleep_t = target_dt - dt.nanosec
- sys.nanosleep(0, sleep_t)
- end
end
redef fun input(input_event)
var entry = entries[path]
if not entry.is_dirty then continue
var name = entry.name
- if entry.has_source then name = entry.src_path.to_s
+ if entry.has_source then name = entry.src_path.as(not null)
if entry.is_new then
print " + {name}"
else
fun need_render(src, target: String): Bool do
if force_render then return true
if not target.file_exists then return true
- return src.file_stat.mtime >= target.file_stat.mtime
+ return src.file_stat.as(not null).mtime >= target.file_stat.as(not null).mtime
end
# Create a new `WikiSection`.
# Used to translate ids in beautiful page names.
fun pretty_name(name: String): String do
name = name.replace("_", " ")
- name = name.capitalized
+ name = name.capitalized(keep_upper=true)
return name
end
end
# Returns `-1` if not `has_source`.
fun create_time: Int do
if not has_source then return -1
- return src_full_path.file_stat.ctime
+ return src_full_path.as(not null).file_stat.as(not null).ctime
end
# Entry last modification time.
# Returns `-1` if not `has_source`.
fun last_edit_time: Int do
if not has_source then return -1
- return src_full_path.file_stat.mtime
+ return src_full_path.as(not null).file_stat.as(not null).mtime
end
# Entry list rendering time.
# Returns `-1` if `is_new`.
fun last_render_time: Int do
if is_new then return -1
- return out_full_path.file_stat.mtime
+ return out_full_path.file_stat.as(not null).mtime
end
# Entries hierarchy
# then returns the main wiki template file.
fun template_file: String do
if is_root then return wiki.config.template_file
- return parent.template_file
+ return parent.as(not null).template_file
end
# Header template file for `self`.
# Behave like `template_file`.
fun header_file: String do
if is_root then return wiki.config.header_file
- return parent.header_file
+ return parent.as(not null).header_file
end
# Footer template file for `self`.
# Behave like `template_file`.
fun footer_file: String do
if is_root then return wiki.config.footer_file
- return parent.footer_file
+ return parent.as(not null).footer_file
end
# Menu template file for `self`.
# Behave like `template_file`.
fun menu_file: String do
if is_root then return wiki.config.menu_file
- return parent.menu_file
+ return parent.as(not null).menu_file
end
# Display the entry `name`.
redef fun title do
if has_config then
- var title = config.title
+ var title = config.as(not null).title
if title != null then return title
end
return super
#
# Hidden section are rendered but not linked in menus.
fun is_hidden: Bool do
- if has_config then return config.is_hidden
+ if has_config then return config.as(not null).is_hidden
return false
end
if parent == null then
return wiki.config.source_dir
else
- return wiki.expand_path(parent.src_path, name)
+ return wiki.expand_path(parent.as(not null).src_path, name)
end
end
# Also check custom config.
redef fun template_file do
if has_config then
- var tpl = config.template_file
+ var tpl = config.as(not null).template_file
if tpl != null then return tpl
end
if is_root then return wiki.config.template_file
- return parent.template_file
+ return parent.as(not null).template_file
end
# Also check custom config.
redef fun header_file do
if has_config then
- var tpl = config.header_file
+ var tpl = config.as(not null).header_file
if tpl != null then return tpl
end
if is_root then return wiki.config.header_file
- return parent.header_file
+ return parent.as(not null).header_file
end
# Also check custom config.
redef fun footer_file do
if has_config then
- var tpl = config.footer_file
+ var tpl = config.as(not null).footer_file
if tpl != null then return tpl
end
if is_root then return wiki.config.footer_file
- return parent.footer_file
+ return parent.as(not null).footer_file
end
# Also check custom config.
redef fun menu_file do
if has_config then
- var tpl = config.menu_file
+ var tpl = config.as(not null).menu_file
if tpl != null then return tpl
end
if is_root then return wiki.config.menu_file
- return parent.menu_file
+ return parent.as(not null).menu_file
end
end
# Articles can only have `WikiSection` as parents.
redef type PARENT: WikiSection
- redef fun title: String do
+ redef fun title do
+ var parent = self.parent
if name == "index" and parent != null then return parent.title
return super
end
content = md
end
- redef var src_full_path: nullable String = null
+ redef var src_full_path = null
redef fun src_path do
var src_full_path = self.src_full_path
# REQUIRE: `has_source`.
var md: nullable String is lazy do
if not has_source then return null
- var file = new FileReader.open(src_full_path.to_s)
+ var file = new FileReader.open(src_full_path.as(not null))
var md = file.read_all
file.close
return md
redef fun is_dirty do
if super then return true
if has_source then
- return wiki.need_render(src_full_path.to_s, out_full_path)
+ return wiki.need_render(src_full_path.as(not null), out_full_path)
end
return false
end
var sidebar_blocks: Array[String] is lazy do
var res = new Array[String]
if not has_key("wiki.sidebar.blocks") then return res
- for val in at("wiki.sidebar.blocks").values do
+ for val in at("wiki.sidebar.blocks").as(not null).values do
res.add val
end
return res
redef class WikiSection
# Output directory (where to ouput the HTML pages for this section).
- redef fun out_path: String do
+ redef fun out_path do
+ var parent = self.parent
if parent == null then
return wiki.config.out_dir
else
# Copy attached files from `src_path` to `out_path`.
private fun copy_files do
assert has_source
- var dir = src_full_path.to_s
+ var dir = src_full_path.as(not null).to_s
for name in dir.files do
if name == wiki.config_filename then continue
if name.has_suffix(".md") then continue
redef class WikiArticle
- redef fun out_path: String do
+ redef fun out_path do
+ var parent = self.parent
if parent == null then
return wiki.expand_path(wiki.config.out_dir, "{name}.html")
else
# Returns `null` if no article can be found.
fun lookup_entry_by_name(context: WikiEntry, name: String): nullable WikiEntry do
var section: nullable WikiEntry = context.parent or else context
- var res = section.lookup_entry_by_name(name)
+ var res = section.as(not null).lookup_entry_by_name(name)
if res != null then return res
while section != null do
if section.name == name then return section
# Returns `null` if no article can be found.
fun lookup_entry_by_title(context: WikiEntry, title: String): nullable WikiEntry do
var section: nullable WikiEntry = context.parent or else context
- var res = section.lookup_entry_by_title(title)
+ var res = section.as(not null).lookup_entry_by_title(title)
if res != null then return res
while section != null do
if section.title.to_lower == title.to_lower then return section
fun is_index: Bool do return name == "index"
redef fun href do
+ var parent = self.parent
if parent == null then
return "{name}.html"
else
# Gen a test db with a random name (to avoid race conditions).
fun gen_test_db: MongoDb do
- var db_name = "test_nitrpg_{get_time}_{1000.rand}"
+ var testid = "NIT_TESTING_ID".environ.to_i
+ var db_name = "test_nitrpg_{testid}"
var db = load_db(db_name)
test_dbs.add db
return db
if json isa JsonParseError then
die("Wrong input file ({json.message})")
abort
+ else if json == null then
+ die("Unable to parse input file as json (got null)")
+ abort
else if not json isa JsonObject then
die("Wrong input type (expected JsonObject got {json.class_name})")
abort
return new RefundStats.from_json(content)
end
- redef fun save_stats(stats: RefundStats) do
+ redef fun save_stats(stats) do
write_output(stats.to_json.to_pretty_json, stats_file)
end
end
proc.check_key(json, "reclamations")
var res = new Array[Reclamation]
var recls = json["reclamations"]
- if not recls isa JsonArray then
+ if recls == null then
+ proc.die("Wrong type for `number` (expected JsonArray got null)")
+ abort
+ else if not recls isa JsonArray then
proc.die("Wrong type for `number` (expected JsonArray got {recls.class_name})")
abort
end
var i = 0
for obj in recls do
- if not obj isa JsonObject then
+ if obj == null then
+ proc.die("Wrong type for `reclamations#{i}` (expected JsonObject got null)")
+ abort
+ else if not obj isa JsonObject then
proc.die("Wrong type for `reclamations#{i}` " +
"(expected JsonObject got {obj.class_name})")
abort
init from_json(proc: RefundProcessor, json: JsonObject) do
proc.check_key(json, "dossier")
var id = json["dossier"]
- if not id isa String then
+ if id == null then
+ proc.die("Wrong type for `dossier` (expected String got null)")
+ abort
+ else if not id isa String then
proc.die("Wrong type for `dossier` (expected String got {id.class_name})")
abort
end
init from_json(proc: RefundProcessor, json: JsonObject) do
proc.check_key(json, "mois")
var month = json["mois"]
- if not month isa String then
+ if month == null then
+ proc.die("Wrong type for `mois` (expected String got null)")
+ return
+ else if not month isa String then
proc.die("Wrong type for `mois` (expected String got {month.class_name})")
return
end
init from_json(proc: RefundProcessor, json: JsonObject) do
proc.check_key(json, "date")
var date = json["date"]
- if not date isa String then
+ if date == null then
+ proc.die("Wrong type for `date` (expected String got null)")
+ abort
+ else if not date isa String then
proc.die("Wrong type for `date` (expected String got {date.class_name})")
abort
end
private fun parse_care_id(proc: RefundProcessor, json: JsonObject): Int do
proc.check_key(json, "soin")
var id = json["soin"]
- if not id isa Int then
+ if id == null then
+ proc.die("Wrong type for `soin` (expected Int got null)")
+ abort
+ else if not id isa Int then
proc.die("Wrong type for `soin` (expected Int got {id.class_name})")
abort
end
private fun parse_fees(proc: RefundProcessor, json: JsonObject): Dollar do
proc.check_key(json, "montant")
var fees = json["montant"]
- if not fees isa String then
+ if fees == null then
+ proc.die("Wrong type for `fees` (expected String got null)")
+ abort
+ else if not fees isa String then
proc.die("Wrong type for `fees` (expected String got {fees.class_name})")
abort
end
print n.message
exit 1
end
- n = n.children.first.children.first.as(not null)
+ n = n.children.first.as(not null).children.first.as(not null)
if n isa Nplan then
print "Error: expected a problem, got a plan."
exit 1
assert n isa Nproblem
# Load all locations
- for n2 in n.n_locations.n_list.children do
+ for n2 in n.n_locations.n_list.as(not null).children do
var e = new Location(locations.length, n2.n_name.text, n2.n_x.text.to_f, n2.n_y.text.to_f)
assert not locations.has_key(e.name)
locations[e.name] = e
# Load all roads
var nbr = 0
- for n2 in n.n_roads.n_list.children do
+ for n2 in n.n_roads.n_list.as(not null).children do
var o = locations.get_or_null(n2.n_orig.text)
var d = locations.get_or_null(n2.n_dest.text)
assert o != null and d != null
# Load the robot
var robot = null
- for n2 in n.n_robots.n_list.children do
+ for n2 in n.n_robots.n_list.as(not null).children do
var name = n2.n_name.text
robot = locations.get_or_null(n2.n_emplacement.text)
assert name == robot_name and robot != null
# Load the parcels
var parcel_locations = new Array[nullable Location]
- for n2 in n.n_parcels.n_list.children do
+ for n2 in n.n_parcels.n_list.as(not null).children do
var name = n2.n_name.text
var e = locations.get_or_null(n2.n_emplacement.text)
assert e != null
print "# {parcels.length} parcels"
# Load the goal of parcels
- for n2 in n.n_goal.n_list.children do
+ for n2 in n.n_goal.n_list.as(not null).children do
var parcel = parcel_by_name.get_or_null(n2.n_name.text)
var e = locations.get_or_null(n2.n_emplacement.text)
assert parcel != null and e != null
print n.message
exit 1
end
- n = n.children.first.children.first.as(not null)
+ n = n.children.first.as(not null).children.first.as(not null)
if n isa Nproblem then
print "Error: expected a plan, got a problem."
exit 1
var res = new Plan(self)
var e = initial_state
var cost = 0.0
- for n2 in n.n_actions.children do
+ for n2 in n.n_actions.as(not null).children do
if n2 isa Naction_load then
var parcel = parcel_by_name.get_or_null(n2.n_parcel.text)
assert parcel != null
var dt = clock.lapse
tick += 1
- var turn = new TTurn(self, tick, dt.to_f, dt.millisec)
+ var turn = new TTurn(self, tick, dt, ((dt-dt.floor)*1000.0).to_i)
return turn
end
--- /dev/null
+all: xymus.net
+
+xymus.net: ../benitlux/src/server/benitlux_restful.nit $(shell ../../bin/nitls -M xymus_net.nit)
+ ../../bin/nitc -o $@ xymus_net.nit
+
+../benitlux/src/server/benitlux_restful.nit:
+ make -C ../benitlux src/server/benitlux_restful.nit
+
+pre-build: ../benitlux/src/server/benitlux_restful.nit
--- /dev/null
+Web server source and config of xymus.net
+
+This module acts also as an example to merge multiple `nitcorn` projects into one server.
+
+See the server online at http://xymus.net/.
--- /dev/null
+[package]
+name=xymus_net
+tags=web,example
+maintainer=Alexis Laferrière <alexis.laf@xymus.net>
+license=Apache-2.0
+[upstream]
+browse=https://github.com/nitlang/nit/tree/master/contrib/xymus.net/
+git=https://github.com/nitlang/nit.git
+git.directory=contrib/xymus.net/
+homepage=http://xymus.net/
+issues=https://github.com/nitlang/nit/issues
# This file is part of NIT ( http://www.nitlanguage.org ).
#
-# Copyright 2014-2015 Alexis Laferrière <alexis.laf@xymus.net>
+# Copyright 2014-2016 Alexis Laferrière <alexis.laf@xymus.net>
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# Use actions defined by contribs
import tnitter
import benitlux::benitlux_controller
+import benitlux::benitlux_restful
import opportunity::opportunity_controller
import nitiwiki::wiki_edit
var tnitter_vh = new VirtualHost("tnitter.xymus.net:80")
var pep8_vh = new VirtualHost("pep8.xymus.net:80")
var benitlux_vh = new VirtualHost("benitlux.xymus.net:80")
+var benitlux_admin_vh = new VirtualHost("localhost:8081")
var factory = new HttpFactory.and_libevent
factory.config.virtual_hosts.add default_vh
factory.config.virtual_hosts.add tnitter_vh
factory.config.virtual_hosts.add pep8_vh
factory.config.virtual_hosts.add benitlux_vh
+factory.config.virtual_hosts.add benitlux_admin_vh
# Ports are open, drop to a low-privileged user if we are root
var user_group = new UserGroup("nitcorn", "nitcorn")
benitlux_vh.routes.add new Route("/static/", shared_file_server)
benitlux_vh.routes.add new Route(null, benitlux_sub)
+benitlux_admin_vh.routes.add new Route(null, new BenitluxAdminAction(benitlux_db))
+
# Opportunity service
var opportunity = new OpportunityWelcome
var opportunity_rest = new OpportunityRESTAction
# Calculate the self-th element of the fibonacci sequence.
fun fibonacci: Int
do
- if self < 2 then
- return 1
- else
- return (self-2).fibonacci + (self-1).fibonacci
- end
- end
+ if self < 2 then return self
+ return (self-2).fibonacci + (self-1).fibonacci
+ end
end
# Print usage and exit.
# See: <http://rosettacode.org/wiki/Perlin_noise>
module perlin_noise
-redef universal Float
- # Smoothened `self`
- fun fade: Float do return self*self*self*(self*(self*6.0-15.0)+10.0)
-end
-
-# Improved noise
-class ImprovedNoise
- # Permutations
- var p: Array[Int] = [151,160,137,91,90,15,
- 131,13,201,95,96,53,194,233,7,225,140,36,103,30,69,142,8,99,37,240,21,10,23,
- 190, 6,148,247,120,234,75,0,26,197,62,94,252,219,203,117,35,11,32,57,177,33,
- 88,237,149,56,87,174,20,125,136,171,168, 68,175,74,165,71,134,139,48,27,166,
- 77,146,158,231,83,111,229,122,60,211,133,230,220,105,92,41,55,46,245,40,244,
- 102,143,54, 65,25,63,161, 1,216,80,73,209,76,132,187,208, 89,18,169,200,196,
- 135,130,116,188,159,86,164,100,109,198,173,186, 3,64,52,217,226,250,124,123,
- 5,202,38,147,118,126,255,82,85,212,207,206,59,227,47,16,58,17,182,189,28,42,
- 223,183,170,213,119,248,152, 2,44,154,163, 70,221,153,101,155,167, 43,172,9,
- 129,22,39,253, 19,98,108,110,79,113,224,232,178,185, 112,104,218,246,97,228,
- 251,34,242,193,238,210,144,12,191,179,162,241, 81,51,145,235,249,14,239,107,
- 49,192,214, 31,181,199,106,157,184, 84,204,176,115,121,50,45,127, 4,150,254,
- 138,236,205,93,222,114,67,29,24,72,243,141,128,195,78,66,215,61,156,180]
-
- # Noise value in [-1..1] at 3d coordinates `x, y, z`
- fun noise(x, y, z: Float): Float
- do
- var xx = x.to_i & 255
- var yy = y.to_i & 255
- var zz = z.to_i & 255
-
- x -= x.floor
- y -= y.floor
- z -= z.floor
-
- var u = x.fade
- var v = y.fade
- var w = z.fade
-
- var a = p[xx ] + yy
- var aa = p[a ] + zz
- var ab = p[a+1 ] + zz
- var b = p[xx+1] + yy
- var ba = p[b ] + zz
- var bb = p[b+1 ] + zz
-
- return w.lerp(v.lerp(u.lerp(grad(p[aa ], x, y, z ),
- grad(p[ba ], x-1.0, y, z )),
- u.lerp(grad(p[ab ], x, y-1.0, z ),
- grad(p[bb ], x-1.0, y-1.0, z ))),
- v.lerp(u.lerp(grad(p[aa+1], x, y, z-1.0),
- grad(p[ba+1], x-1.0, y, z-1.0)),
- u.lerp(grad(p[ab+1], x, y-1.0, z-1.0),
- grad(p[bb+1], x-1.0, y-1.0, z-1.0))))
- end
-
- # Value at a corner of the grid
- fun grad(hash: Int, x, y, z: Float): Float
- do
- var h = hash & 15
- var u = if h < 8 then x else y
- var v = if h < 4 then y else if h == 12 or h == 14 then x else z
- return (if h.is_even then u else -u) + (if h & 2 == 0 then v else -v)
- end
-end
+import noise
var map = new ImprovedNoise
print map.noise(3.14, 42.0, 7.0).to_precision(17)
end
end
+ # Find the closest node accepted by `cond` under `max_cost`
+ fun find_closest(max_cost: Int, context: PathContext, cond: nullable TargetCondition[N]): nullable N
+ do
+ var path = path_to_alts(null, max_cost, context, cond)
+ if path == null then return null
+ return path.nodes.last
+ end
+
# We customize the serialization process to avoid problems with recursive
# serialization engines. These engines, such as `JsonSerializer`,
# are at danger to serialize the graph as a very deep tree.
`}
fun action: AMotionEventAction `{ return AMotionEvent_getAction(self); `}
+
+ fun native_down_time: Int `{ return AMotionEvent_getDownTime(self); `}
end
private extern class AMotionEventAction `{ int32_t `}
return null
end
end
+
+ # Time when the user originally pressed down to start a stream of position events
+ #
+ # The return value is in the `java.lang.System.nanoTime()` time base.
+ fun down_time: Int do return native.native_down_time
end
# A pointer event
module bucketed_game is serialize
import serialization
+import counter
# Something acting on the game
abstract class Turnable[G: Game]
private var buckets: Array[BUCKET] =
[for b in n_buckets.times do new HashSet[Bucketable[G]]] is lazy
+ # Stats on delays asked when adding an event with `act_in` and `act_next`
+ private var delays = new Counter[Int]
+
# Add the Bucketable event `e` at `at_tick`.
fun add_at(e: Bucketable[G], at_tick: Int)
do
end
end
end
+
+ # Get some statistics on both the current held events and historic expired events
+ fun stats: String
+ do
+ var entries = 0
+ var instances = new HashSet[Bucketable[G]]
+ var max = 0
+ var min = 100000
+ for bucket in buckets do
+ var len = bucket.length
+ entries += len
+ instances.add_all bucket
+ min = min.min(len)
+ max = max.max(len)
+ end
+ var avg = entries.to_f / buckets.length.to_f
+
+ return "{buckets.length} buckets; uniq/tot:{instances.length}/{entries}, avg:{avg.to_precision(1)}, min:{min}, max:{max}\n" +
+ "history:{delays.sum}, avg:{delays.avg}, min:{delays[delays.min.as(not null)]}, max:{delays[delays.max.as(not null)]}"
+ end
end
# Game related event
# Game logic on the client
class ThinGame
- # Game tick when `self` should act.
+ # Current game tick
#
# Default is 0.
- var tick: Int = 0 is protected writable
+ var tick: Int = 0 is writable
end
# Game turn on the client
class ThinGameTurn[G: ThinGame]
- # Game tick when `self` should act.
+ # Game tick when happened this turn
var tick: Int is protected writable
# Game events occurred for `self`.
end
# Insert the Bucketable event `e` to be executed at next tick.
- fun act_next(e: Bucketable[G]) do game.buckets.add_at(e, tick + 1)
+ fun act_next(e: Bucketable[G])
+ do
+ game.buckets.add_at(e, tick + 1)
+ game.buckets.delays.inc(1)
+ end
# Insert the Bucketable event `e` to be executed at tick `t`.
- fun act_in(e: Bucketable[G], t: Int) do game.buckets.add_at(e, tick + t)
+ fun act_in(e: Bucketable[G], t: Int)
+ do
+ game.buckets.add_at(e, tick + t)
+ game.buckets.delays.inc(t)
+ end
# Add and `apply` a game `event`.
fun add_event( event : GameEvent )
var res = 23 + length
# Note: the order of the elements must not change the hash value.
# So, unlike usual hash functions, the accumulator is not combined with itself.
- for e in self do res += e.hash
+ for e in self do
+ if e != null then res += e.hash
+ end
return res
end
redef fun [](index)
do
assert index: index >= 0 and index < _length
- return _items[index]
+ return _items.as(not null)[index]
end
redef fun []=(index, item)
if _length <= index then
_length = index + 1
end
- _items[index] = item
+ _items.as(not null)[index] = item
end
redef fun add(item)
enlarge(l + 1)
end
_length = l + 1
- _items[l] = item
+ _items.as(not null)[l] = item
end
# Slight optimization for arrays
if items isa Array[E] then
var k = 0
while l < nl do
- _items[l] = items._items[k]
+ _items.as(not null)[l] = items._items.as(not null)[k]
l += 1
k += 1
end
else
for item in items do
- _items[l] = item
+ _items.as(not null)[l] = item
l += 1
end
end
if cap <= c then return
while c <= cap do c = c * 2 + 2
var a = new NativeArray[E](c)
- if _capacity > 0 then _items.copy_to(a, _length)
+ if _capacity > 0 then _items.as(not null).copy_to(a, _length)
_items = a
_capacity = c
end
# Efficient implementation
var l = length
if l != o.length then return false
+ if l == 0 then return true
var i = 0
- var it = _items
- var oit = o._items
+ var it = _items.as(not null)
+ var oit = o._items.as(not null)
while i < l do
if it[i] != oit[i] then return false
i += 1
redef fun <=>(o)
do
- var it = _items
- var oit = o._items
var i = 0
var l = length
+ if l == 0 then return 0
+ var it = _items.as(not null)
+ var oit = o._items.as(not null)
var ol = o.length
var len
if l < ol then len = l else len = ol
# Access
- redef fun [](index) do return get_node(index).item
+ redef fun [](index) do return get_node(index).as(not null).item
- redef fun []=(index, item) do get_node(index).item = item
+ redef fun []=(index, item) do get_node(index).as(not null).item = item
# O(1)
- redef fun first do return _head.item
+ redef fun first do return _head.as(not null).item
# O(1)
- redef fun first=(e) do _head.item = e
+ redef fun first=(e) do _head.as(not null).item = e
# O(1)
- redef fun last do return _tail.item
+ redef fun last do return _tail.as(not null).item
# O(1)
- redef fun last=(e) do _tail.item = e
+ redef fun last=(e) do _tail.as(not null).item = e
# Queries
redef fun push(e)
do
var node = new ListNode[E](e)
- if _tail == null then
+ var tail = _tail
+ if tail == null then
_head = node
else
- _tail.next = node
- node.prev = _tail
+ tail.next = node
+ node.prev = tail
end
_tail = node
length += 1
redef fun unshift(e)
do
var node = new ListNode[E](e)
- if _head == null then
+ var head = _head
+ if head == null then
_tail = node
else
- node.next = _head
- _head.prev = node
+ node.next = head
+ head.prev = node
end
_head = node
length += 1
# O(1)
fun link(l: List[E])
do
- if _tail == null then
+ var tail = _tail
+ if tail == null then
_head = l._head
else if l._head != null then
- _tail.next = l._head
- _tail.next.prev = _tail
+ tail.next = l._head
+ tail.next.as(not null).prev = tail
end
_tail = l._tail
length += l.length
# O(1)
redef fun pop
do
- var node = _tail
+ var node = _tail.as(not null)
_tail = node.prev
node.prev = null
if _tail == null then
_head = null
else
- _tail.next = null
+ _tail.as(not null).next = null
end
length -= 1
return node.item
# O(1)
redef fun shift
do
- var node = _head
+ var node = _head.as(not null)
_head = node.next
node.next = null
if _head == null then
_tail = null
else
- _head.prev = null
+ _head.as(not null).prev = null
end
length -= 1
return node.item
if node.next == null then
_tail = null
else
- node.next.prev = null
+ node.next.as(not null).prev = null
end
else if node.next == null then
_tail = node.prev
- node.prev.next = null
+ node.prev.as(not null).next = null
else
- node.prev.next = node.next
- node.next.prev = node.prev
+ node.prev.as(not null).next = node.next
+ node.next.as(not null).prev = node.prev
end
end
# This is the iterator class of List
class ListIterator[E]
super IndexedIterator[E]
- redef fun item do return _node.item
+ redef fun item do return _node.as(not null).item
# Set item `e` at self `index`.
- fun item=(e: E) do _node.item = e
+ fun item=(e: E) do _node.as(not null).item = e
redef fun is_ok do return not _node == null
redef fun next
do
- _node = _node.next
+ _node = _node.as(not null).next
_index += 1
end
redef fun next
do
- _node = _node.prev
+ _node = _node.as(not null).prev
_index -= 1
end
redef fun to_s do
var e = maybe_error
if e != null then return e.to_s
- return value.to_s
+ return value.as(not null).to_s
end
end
var args = new FlatBuffer
var l = 1 # Number of elements in args
args.append(command)
+ var arguments = self.arguments
if arguments != null then
for a in arguments do
args.add('\0')
do
return command.to_cstring.system
end
+
+ # The pid of the program
+ fun pid: Int `{ return getpid(); `}
end
redef class NativeString
# Return null in case of error
fun file_stat: nullable FileStat
do
- var stat = _file.file_stat
+ var stat = _file.as(not null).file_stat
if stat.address_is_null then return null
return new FileStat(stat)
end
# File descriptor of this file
- fun fd: Int do return _file.fileno
+ fun fd: Int do return _file.as(not null).fileno
redef fun close
do
- if _file == null then return
- if _file.address_is_null then
+ var file = _file
+ if file == null then return
+ if file.address_is_null then
if last_error != null then return
last_error = new IOError("Cannot close unopened file")
return
end
- var i = _file.io_close
+ var i = file.io_close
if i != 0 then
last_error = new IOError("Close failed due to error {sys.errno.strerror}")
end
# * `buffer_mode_none`
fun set_buffering_mode(buf_size, mode: Int) do
if buf_size <= 0 then buf_size = 512
- if _file.set_buffering_type(buf_size, mode) != 0 then
+ if _file.as(not null).set_buffering_type(buf_size, mode) != 0 then
last_error = new IOError("Error while changing buffering type for FileStream, returned error {sys.errno.strerror}")
end
end
# assert l == f.read_line
fun reopen
do
- if not eof and not _file.address_is_null then close
+ if not eof and not _file.as(not null).address_is_null then close
last_error = null
- _file = new NativeFile.io_open_read(path.to_cstring)
- if _file.address_is_null then
+ _file = new NativeFile.io_open_read(path.as(not null).to_cstring)
+ if _file.as(not null).address_is_null then
last_error = new IOError("Cannot open `{path.as(not null)}`: {sys.errno.strerror}")
end_reached = true
return
redef fun fill_buffer
do
- var nb = _file.io_read(_buffer, _buffer_capacity)
- if last_error == null and _file.ferror then
+ var nb = _file.as(not null).io_read(_buffer, _buffer_capacity)
+ if last_error == null and _file.as(not null).ferror then
last_error = new IOError("Cannot read `{path.as(not null)}`: {sys.errno.strerror}")
end_reached = true
end
self.path = path
prepare_buffer(100)
_file = new NativeFile.io_open_read(path.to_cstring)
- if _file.address_is_null then
+ if _file.as(not null).address_is_null then
last_error = new IOError("Cannot open `{path}`: {sys.errno.strerror}")
end_reached = true
end
self.path = ""
prepare_buffer(1)
_file = fd.fd_to_stream(read_only)
- if _file.address_is_null then
+ if _file.as(not null).address_is_null then
last_error = new IOError("Error: Converting fd {fd} to stream failed with '{sys.errno.strerror}'")
end_reached = true
end
last_error = new IOError("Cannot write to non-writable stream")
return
end
- if _file.address_is_null then
+ if _file.as(not null).address_is_null then
last_error = new IOError("Writing on a null stream")
_is_writable = false
return
end
- var err = _file.write_byte(value)
+ var err = _file.as(not null).write_byte(value)
if err != 1 then
# Big problem
last_error = new IOError("Problem writing a byte: {err}")
last_error = new IOError("Cannot write to non-writable stream")
return
end
- if _file.address_is_null then
+ if _file.as(not null).address_is_null then
last_error = new IOError("Writing on a null stream")
_is_writable = false
return
end
- var err = _file.io_write(native, from, len)
+ var err = _file.as(not null).io_write(native, from, len)
if err != len then
# Big problem
last_error = new IOError("Problem in writing : {err} {len} \n")
_file = new NativeFile.io_open_write(path.to_cstring)
self.path = path
_is_writable = true
- if _file.address_is_null then
+ if _file.as(not null).address_is_null then
last_error = new IOError("Cannot open `{path}`: {sys.errno.strerror}")
is_writable = false
end
self.path = ""
_file = fd.fd_to_stream(wipe_write)
_is_writable = true
- if _file.address_is_null then
+ if _file.as(not null).address_is_null then
last_error = new IOError("Error: Opening stream from file descriptor {fd} failed with '{sys.errno.strerror}'")
_is_writable = false
end
return res
end
+ # Is `self` the path to an existing directory ?
+ #
+ # ~~~nit
+ # assert ".".to_path.is_dir
+ # assert not "/etc/issue".to_path.is_dir
+ # assert not "/should/not/exist".to_path.is_dir
+ # ~~~
+ fun is_dir: Bool do
+ var st = stat
+ if st == null then return false
+ return st.is_dir
+ end
+
# Delete a directory and all of its content
#
# Does not go through symbolic links and may get stuck in a cycle if there
end
return res
end
+
+ # Is `self` a power of two ?
+ #
+ # ~~~nit
+ # assert not 3.is_pow2
+ # assert 2.is_pow2
+ # assert 1.is_pow2
+ # assert not 0.is_pow2
+ # ~~~
+ fun is_pow2: Bool do return self != 0 and (self & self - 1) == 0
end
redef class Byte
# Cache of a single `regmatch_t` to prevent many calls to `malloc`
private var native_match: NativeMatchArray is lazy do
native_match_is_init = true
- return new NativeMatchArray.malloc(native.re_nsub+1)
+ return new NativeMatchArray.malloc(native.as(not null).re_nsub+1)
end
private var native_match_is_init = false
# Letters that follow a letter are lowercased
# Letters that follow a non-letter are upcased.
#
+ # If `keep_upper = true`, already uppercase letters are not lowercased.
+ #
# SEE : `Char::is_letter` for the definition of letter.
#
# assert "jAVASCRIPT".capitalized == "Javascript"
# assert "i am root".capitalized == "I Am Root"
# assert "ab_c -ab0c ab\nc".capitalized == "Ab_C -Ab0C Ab\nC"
- fun capitalized: SELFTYPE do
+ # assert "preserve my ACRONYMS".capitalized(keep_upper=true) == "Preserve My ACRONYMS"
+ fun capitalized(keep_upper: nullable Bool): SELFTYPE do
if length == 0 then return self
var buf = new Buffer.with_cap(length)
-
- var curr = chars[0].to_upper
- var prev = curr
- buf[0] = curr
-
- for i in [1 .. length[ do
- prev = curr
- curr = self[i]
- if prev.is_letter then
- buf[i] = curr.to_lower
- else
- buf[i] = curr.to_upper
- end
- end
-
+ buf.capitalize(keep_upper=keep_upper, src=self)
return buf.to_s
end
end
# Letters that follow a letter are lowercased
# Letters that follow a non-letter are upcased.
#
+ # If `keep_upper = true`, uppercase letters are not lowercased.
+ #
+ # When `src` is specified, this method reads from `src` instead of `self`
+ # but it still writes the result to the beginning of `self`.
+ # This requires `self` to have the capacity to receive all of the
+ # capitalized content of `src`.
+ #
# SEE: `Char::is_letter` for the definition of a letter.
#
# var b = new FlatBuffer.from("jAVAsCriPt")
# b = new FlatBuffer.from("ab_c -ab0c ab\nc")
# b.capitalize
# assert b == "Ab_C -Ab0C Ab\nC"
- fun capitalize do
+ #
+ # b = new FlatBuffer.from("12345")
+ # b.capitalize(src="foo")
+ # assert b == "Foo45"
+ #
+ # b = new FlatBuffer.from("preserve my ACRONYMS")
+ # b.capitalize(keep_upper=true)
+ # assert b == "Preserve My ACRONYMS"
+ fun capitalize(keep_upper: nullable Bool, src: nullable Text) do
+ src = src or else self
+ var length = src.length
if length == 0 then return
- var c = self[0].to_upper
+ keep_upper = keep_upper or else false
+
+ var c = src[0].to_upper
self[0] = c
var prev = c
for i in [1 .. length[ do
prev = c
- c = self[i]
+ c = src[i]
if prev.is_letter then
- self[i] = c.to_lower
+ if keep_upper then
+ self[i] = c
+ else
+ self[i] = c.to_lower
+ end
else
self[i] = c.to_upper
end
# see `alpha_comparator`
private class AlphaComparator
super Comparator
- redef fun compare(a, b) do return a.to_s <=> b.to_s
+ redef fun compare(a, b) do
+ if a == b then return 0
+ if a == null then return -1
+ if b == null then return 1
+ return a.to_s <=> b.to_s
+ end
end
# Stateless comparator that naively use `to_s` to compare things.
# SEE: `abstract_text::Text` for more info on the difference
# between `Text::bytelen` and `Text::length`.
fun to_s_full(bytelen, unilen: Int): String is abstract
+
+ # Copies the content of `src` to `self`
+ #
+ # NOTE: `self` must be large enough to withold `self.bytelen` bytes
+ fun fill_from(src: Text) do src.copy_to_native(self, src.bytelen, 0, 0)
end
redef class NativeArray[E]
end
return res
end
+
+ redef fun copy_to_native(dst, n, src_off, dst_off) do
+ _items.copy_to(dst, n, first_byte + src_off, dst_off)
+ end
end
# Immutable strings of characters.
end
redef fun copy_to_native(dest, n, src_offset, dest_offset) do
- var subs = new RopeSubstrings.from(self, src_offset)
- var st = src_offset - subs.pos
- var off = dest_offset
- while n > 0 do
- var it = subs.item
- if n > it.length then
- var cplen = it.length - st
- it._items.copy_to(dest, cplen, st, off)
- off += cplen
- n -= cplen
- else
- it._items.copy_to(dest, n, st, off)
- n = 0
- end
- subs.next
- st = 0
+ var l = _left
+ if src_offset < l.bytelen then
+ var lcopy = l.bytelen - src_offset
+ lcopy = if lcopy > n then n else lcopy
+ l.copy_to_native(dest, lcopy, src_offset, dest_offset)
+ dest_offset += lcopy
+ n -= lcopy
+ src_offset = 0
end
+ _right.copy_to_native(dest, n, src_offset, dest_offset)
end
# Returns a balanced version of `self`
redef fun next do
if pos < 0 then return
var curr = iter.prev
- var currit = curr.node
+ var currit = curr.as(not null).node
while curr != null do
currit = curr.node
if not currit isa Concat then
redef fun next do
pos += str.length
if pos > max then return
- var it = iter.prev
+ var it = iter.prev.as(not null)
var rnod = it.node
loop
if not rnod isa Concat then
it.ldone = true
it.rdone = true
str = rnod.as(FlatString)
- iter = it.as(not null)
+ iter = it
break
end
if not it.ldone then
rnod = rnod._right
it = new RopeCharIteratorPiece(rnod, false, false, it)
else
- it = it.prev
+ it = it.prev.as(not null)
rnod = it.node
continue
end
module crapto
import english_utils
+import xor
--- /dev/null
+HUIfTQsPAh9PE048GmllH0kcDk4TAQsHThsBFkU2AB4BSWQgVB0dQzNTTmVS
+BgBHVBwNRU0HBAxTEjwMHghJGgkRTxRMIRpHKwAFHUdZEQQJAGQmB1MANxYG
+DBoXQR0BUlQwXwAgEwoFR08SSAhFTmU+Fgk4RQYFCBpGB08fWXh+amI2DB0P
+QQ1IBlUaGwAdQnQEHgFJGgkRAlJ6f0kASDoAGhNJGk9FSA8dDVMEOgFSGQEL
+QRMGAEwxX1NiFQYHCQdUCxdBFBZJeTM1CxsBBQ9GB08dTnhOSCdSBAcMRVhI
+CEEATyBUCHQLHRlJAgAOFlwAUjBpZR9JAgJUAAELB04CEFMBJhAVTQIHAh9P
+G054MGk2UgoBCVQGBwlTTgIQUwg7EAYFSQ8PEE87ADpfRyscSWQzT1QCEFMa
+TwUWEXQMBk0PAg4DQ1JMPU4ALwtJDQhOFw0VVB1PDhxFXigLTRkBEgcKVVN4
+Tk9iBgELR1MdDAAAFwoFHww6Ql5NLgFBIg4cSTRWQWI1Bk9HKn47CE8BGwFT
+QjcEBx4MThUcDgYHKxpUKhdJGQZZVCFFVwcDBVMHMUV4LAcKQR0JUlk3TwAm
+HQdJEwATARNFTg5JFwQ5C15NHQYEGk94dzBDADsdHE4UVBUaDE5JTwgHRTkA
+Umc6AUETCgYAN1xGYlUKDxJTEUgsAA0ABwcXOwlSGQELQQcbE0c9GioWGgwc
+AgcHSAtPTgsAABY9C1VNCAINGxgXRHgwaWUfSQcJABkRRU8ZAUkDDTUWF01j
+OgkRTxVJKlZJJwFJHQYADUgRSAsWSR8KIgBSAAxOABoLUlQwW1RiGxpOCEtU
+YiROCk8gUwY1C1IJCAACEU8QRSxORTBSHQYGTlQJC1lOBAAXRTpCUh0FDxhU
+ZXhzLFtHJ1JbTkoNVDEAQU4bARZFOwsXTRAPRlQYE042WwAuGxoaAk5UHAoA
+ZCYdVBZ0ChQLSQMYVAcXQTwaUy1SBQsTAAAAAAAMCggHRSQJExRJGgkGAAdH
+MBoqER1JJ0dDFQZFRhsBAlMMIEUHHUkPDxBPH0EzXwArBkkdCFUaDEVHAQAN
+U29lSEBAWk44G09fDXhxTi0RAk4ITlQbCk0LTx4cCjBFeCsGHEETAB1EeFZV
+IRlFTi4AGAEORU4CEFMXPBwfCBpOAAAdHUMxVVUxUmM9ElARGgZBAg4PAQQz
+DB4EGhoIFwoKUDFbTCsWBg0OTwEbRSonSARTBDpFFwsPCwIATxNOPBpUKhMd
+Th5PAUgGQQBPCxYRdG87TQoPD1QbE0s9GkFiFAUXR0cdGgkADwENUwg1DhdN
+AQsTVBgXVHYaKkg7TgNHTB0DAAA9DgQACjpFX0BJPQAZHB1OeE5PYjYMAg5M
+FQBFKjoHDAEAcxZSAwZOBREBC0k2HQxiKwYbR0MVBkVUHBZJBwp0DRMDDk5r
+NhoGACFVVWUeBU4MRREYRVQcFgAdQnQRHU0OCxVUAgsAK05ZLhdJZChWERpF
+QQALSRwTMRdeTRkcABcbG0M9Gk0jGQwdR1ARGgNFDRtJeSchEVIDBhpBHQlS
+WTdPBzAXSQ9HTBsJA0UcQUl5bw0KB0oFAkETCgYANlVXKhcbC0sAGgdFUAIO
+ChZJdAsdTR0HDBFDUk43GkcrAAUdRyonBwpOTkJEUyo8RR8USSkOEENSSDdX
+RSAdDRdLAA0HEAAeHQYRBDYJC00MDxVUZSFQOV1IJwYdB0dXHRwNAA9PGgMK
+OwtTTSoBDBFPHU54W04mUhoPHgAdHEQAZGU/OjV6RSQMBwcNGA5SaTtfADsX
+GUJHWREYSQAnSARTBjsIGwNOTgkVHRYANFNLJ1IIThVIHQYKAGQmBwcKLAwR
+DB0HDxNPAU94Q083UhoaBkcTDRcAAgYCFkU1RQUEBwFBfjwdAChPTikBSR0T
+TwRIEVIXBgcURTULFk0OBxMYTwFUN0oAIQAQBwkHVGIzQQAGBR8EdCwRCEkH
+ElQcF0w0U05lUggAAwANBxAAHgoGAwkxRRMfDE4DARYbTn8aKmUxCBsURVQf
+DVlOGwEWRTIXFwwCHUEVHRcAMlVDKRsHSUdMHQMAAC0dCAkcdCIeGAxOazkA
+BEk2HQAjHA1OAFIbBxNJAEhJBxctDBwKSRoOVBwbTj8aQS4dBwlHKjUECQAa
+BxscEDMNUhkBC0ETBxdULFUAJQAGARFJGk9FVAYGGlMNMRcXTRoBDxNPeG43
+TQA7HRxJFUVUCQhBFAoNUwctRQYFDE43PT9SUDdJUydcSWRtcwANFVAHAU5T
+FjtFGgwbCkEYBhlFeFsABRcbAwZOVCYEWgdPYyARNRcGAQwKQRYWUlQwXwAg
+ExoLFAAcARFUBwFOUwImCgcDDU5rIAcXUj0dU2IcBk4TUh0YFUkASEkcC3QI
+GwMMQkE9SB8AMk9TNlIOCxNUHQZCAAoAHh1FXjYCDBsFABkOBkk7FgALVQRO
+D0EaDwxOSU8dGgI8EVIBAAUEVA5SRjlUQTYbCk5teRsdRVQcDhkDADBFHwhJ
+AQ8XClJBNl4AC1IdBghVEwARABoHCAdFXjwdGEkDCBMHBgAwW1YnUgAaRyon
+B0VTGgoZUwE7EhxNCAAFVAMXTjwaTSdSEAESUlQNBFJOZU5LXHQMHE0EF0EA
+Bh9FeRp5LQdFTkAZREgMU04CEFMcMQQAQ0lkay0ABwcqXwA1FwgFAk4dBkIA
+CA4aB0l0PD1MSQ8PEE87ADtbTmIGDAILAB0cRSo3ABwBRTYKFhROHUETCgZU
+MVQHYhoGGksABwdJAB0ASTpFNwQcTRoDBBgDUkksGioRHUkKCE5THEVCC08E
+EgF0BBwJSQoOGkgGADpfADETDU5tBzcJEFMLTx0bAHQJCx8ADRJUDRdMN1RH
+YgYGTi5jMURFeQEaSRAEOkURDAUCQRkKUmQ5XgBIKwYbQFIRSBVJGgwBGgtz
+RRNNDwcVWE8BT3hJVCcCSQwGQx9IBE4KTwwdASEXF01jIgQATwZIPRpXKwYK
+BkdEGwsRTxxDSToGMUlSCQZOFRwKUkQ5VEMnUh0BR0MBGgAAZDwGUwY7CBdN
+HB5BFwMdUz0aQSwWSQoITlMcRUILTxoCEDUXF01jNw4BTwVBNlRBYhAIGhNM
+EUgIRU5CRFMkOhwGBAQLTVQOHFkvUkUwF0lkbXkbHUVUBgAcFA0gRQYFCBpB
+PU8FQSsaVycTAkJHYhsRSQAXABxUFzFFFggICkEDHR1OPxoqER1JDQhNEUgK
+TkJPDAUAJhwQAg0XQRUBFgArU04lUh0GDlNUGwpOCU9jeTY1HFJARE4xGA4L
+ACxSQTZSDxsJSw1ICFUdBgpTNjUcXk0OAUEDBxtUPRpCLQtFTgBPVB8NSRoK
+SREKLUUVAklkERgOCwAsUkE2Ug8bCUsNSAhVHQYKUyI7RQUFABoEVA0dWXQa
+Ry1SHgYOVBFIB08XQ0kUCnRvPgwQTgUbGBwAOVREYhAGAQBJEUgETgpPGR8E
+LUUGBQgaQRIaHEshGk03AQANR1QdBAkAFwAcUwE9AFxNY2QxGA4LACxSQTZS
+DxsJSw1ICFUdBgpTJjsIF00GAE1ULB1NPRpPLF5JAgJUVAUAAAYKCAFFXjUe
+DBBOFRwOBgA+T04pC0kDElMdC0VXBgYdFkU2CgtNEAEUVBwTWXhTVG5SGg8e
+AB0cRSo+AwgKRSANExlJCBQaBAsANU9TKxFJL0dMHRwRTAtPBRwQMAAATQcB
+FlRlIkw5QwA2GggaR0YBBg5ZTgIcAAw3SVIaAQcVEU8QTyEaYy0fDE4ITlhI
+Jk8DCkkcC3hFMQIEC0EbAVIqCFZBO1IdBgZUVA4QTgUWSR4QJwwRTWM=
--- /dev/null
+# This file is part of NIT ( http://www.nitlanguage.org ).
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+
+import base64
+import crapto
+
+# Check usage
+if args.length != 1 then
+ print "Usage: repeating_key_xor_solve <cipher_file>"
+ exit 1
+end
+
+# Read the cipher from the file
+var cipher_bytes = args[0].to_path.read_all_bytes.decode_base64
+
+# Create a RepeatingKeyXorCipher object to manipulate your ciphertext
+var xorcipher = new RepeatingKeyXorCipher
+xorcipher.ciphertext = cipher_bytes
+
+# Try to find the best candidate key
+xorcipher.find_key
+
+# Decrypt the cipher according to the found key
+xorcipher.decrypt
+
+# Check the resulting plaintext out...
+print xorcipher.plaintext
--- /dev/null
+# This file is part of NIT ( http://www.nitlanguage.org ).
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+
+# Cryptographic attacks and utilities for XOR-based algorithms.
+module xor
+
+import combinations
+import crypto
+import english_utils
+
+redef class SingleByteXorCipher
+ # Tries to find key using frequency analysis on all possible plaintexts.
+ # Populates `self.key`
+ fun find_key do
+
+ # Accumulate best result
+ var max = 0.0
+ var best = 0.to_b
+
+ # Iterate on possible values for a byte
+ var xor_b = new Bytes.with_capacity(1)
+ for b in [0 .. 255] do
+ # Need `Bytes` to pass to xor
+ xor_b[0] = b.to_b
+
+ # Xor and evaluate result
+ var xored = ciphertext.xorcipher(xor_b)
+ var result = xored.to_s.english_scoring
+ if result > max then
+ max = result
+ best = b.to_b
+ end
+ end
+
+ self.key = best
+
+ end
+end
+
+redef class RepeatingKeyXorCipher
+ # Attempts to find the key by using frequency analysis on the resulting plaintexts.
+ # Best key lengths are estimated using the hamming distance of blocks of keylength bytes.
+ # Ciphertext is then transposed in such a way that it can be solved by sequences of
+ # SingleByteXor (one for each offset in the key).
+ #
+ # `min_keylength` and `max_keylength` are limits as to what key lengths are tested.
+ # `considered_keylength_count` is the number of best key lengths that are kept to be
+ # analysed by the SingleByteXor frequency analysis.
+ fun find_key(min_keylength, max_keylength, considered_keylength_count: nullable Int) do
+
+ # Set default values
+ if min_keylength == null then min_keylength = 2
+ if max_keylength == null then max_keylength = 40
+ if considered_keylength_count == null then considered_keylength_count = 3
+
+ # Find the best candidate key lengths based on the normalized hamming distances
+ var best_sizes = get_normalized_hamming_distances(min_keylength, max_keylength, considered_keylength_count)
+
+ var best = 0.0
+ var best_key: nullable Bytes = null
+ for ks in best_sizes do
+
+ # Rearrange ciphertext to be in SingleByteXORable blocks
+ var transposed = transpose_ciphertext(ks)
+
+ var key = new Bytes.empty
+ for slot in transposed do
+ var sbx = new SingleByteXorCipher
+ sbx.ciphertext = slot
+ sbx.find_key
+ key.add sbx.key
+ end
+
+ # Evaluate the resulting plaintext based on english frequency analysis
+ var eng_score = ciphertext.xorcipher(key).to_s.english_scoring
+ if eng_score > best then
+ best_key = key
+ best = eng_score
+ end
+
+ assert best_key != null
+ self.key = best_key
+
+ end
+ end
+
+ # Computes the normalized hamming distances between blocks of ciphertext of length between `min_length` and `max_length`.
+ # The `considered_keylength_count` smallest results are returned
+ private fun get_normalized_hamming_distances(min_keylength, max_keylength, considered_keylength_count: Int): Array[Int] do
+
+ var normalized_distances = new HashMap[Float, Int]
+
+ # Iterate over all given key lengths
+ for ks in [min_keylength .. max_keylength[ do
+
+ # Initialize the blocks of size `ks`
+ var blocks = new Array[Bytes]
+ while (blocks.length + 1) * ks < ciphertext.length do
+ blocks.add(ciphertext.slice(blocks.length * ks, ks))
+ end
+
+ # Compute the normalized hamming distance with all block combinations
+ var pairs = new CombinationCollection[Bytes](blocks, 2)
+ var hamming_dists = new Array[Float]
+ for p in pairs do
+ hamming_dists.add(p[0].hamming_distance(p[1]).to_f / ks.to_f)
+ end
+
+ # Normalize the results based on the number of blocks
+ var normalized = 0.0
+ for dist in hamming_dists do normalized += dist
+ normalized /= hamming_dists.length.to_f
+ normalized_distances[normalized] = ks
+
+ end
+
+ # Collect the best candidates
+ var distances = normalized_distances.keys.to_a
+ default_comparator.sort(distances)
+ var best_distances = distances.subarray(0, considered_keylength_count)
+ var best_sizes = [for d in best_distances do normalized_distances[d]]
+
+ return best_sizes
+ end
+
+ # Returns a rearranged format of the ciphertext where every byte of a slot will be XORed with the same offset of a key of length `keylength`.
+ private fun transpose_ciphertext(keylength: Int): Array[Bytes] do
+ var transposed = new Array[Bytes]
+ for i in [0 .. keylength[ do
+ transposed.add(new Bytes.empty)
+ end
+
+ for byte_idx in [0 .. ciphertext.length[ do
+ transposed[byte_idx % keylength].add(ciphertext[byte_idx])
+ end
+
+ return transposed
+ end
+end
# See the License for the specific language governing permissions and
# limitations under the License.
-# Mix of all things cryptography-related
-module crypto
+# Basic cryptographic ciphers and utilities.
+module basic_ciphers
redef class Char
# Rotates self of `x`
end
redef class Bytes
-
- # Returns `self` xored with `key`
- #
- # The key is cycled through until the `self` has been completely xored.
- #
- # assert "goodmorning".to_bytes.xorcipher(" ".to_bytes) == "GOODMORNING".bytes
- fun xorcipher(key: Bytes): Bytes do
- var xored = new Bytes.with_capacity(self.length)
-
- for i in self.length.times do
- xored.add(self[i] ^ key[i % key.length])
+ # Computes the edit/hamming distance of two sequences of bytes.
+ #
+ # assert "this is a test".to_bytes.hamming_distance("wokka wokka!!!".bytes) == 37
+ # assert "this is a test".to_bytes.hamming_distance("this is a test".bytes) == 0
+ #
+ fun hamming_distance(other: SequenceRead[Byte]): Int do
+ var diff = 0
+ for idx in self.length.times do
+ var res_byte = self[idx] ^ other[idx]
+ for bit in [0..8[ do
+ if res_byte & 1u8 == 1u8 then diff += 1
+ res_byte = res_byte >> 1
+ end
end
-
- return xored
+ return diff
end
end
--- /dev/null
+# This file is part of NIT ( http://www.nitlanguage.org ).
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+
+# Mix of all things cryptography-related
+module crypto
+
+import basic_ciphers
+import xor_ciphers
[upstream]
browse=https://github.com/nitlang/nit/tree/master/lib/crypto.nit
git=https://github.com/nitlang/nit.git
-git.directory=lib/crypto.nit
+git.directory=lib/crypto/crypto.nit
homepage=http://nitlanguage.org
issues=https://github.com/nitlang/nit/issues
--- /dev/null
+# This file is part of NIT ( http://www.nitlanguage.org ).
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+
+# XOR oriented cryptographic ciphers and utilities.
+module xor_ciphers
+
+redef class Bytes
+ # Returns `self` xored with `key`
+ #
+ # The key is cycled through until the `self` has been completely xored.
+ #
+ # assert "goodmorning".to_bytes.xorcipher(" ".to_bytes) == "GOODMORNING".bytes
+ fun xorcipher(key: Bytes): Bytes do
+ var xored = new Bytes.with_capacity(self.length)
+
+ for i in self.length.times do
+ xored.add(self[i] ^ key[i % key.length])
+ end
+
+ return xored
+ end
+end
+
+# Base class to modelize cryptographic ciphers
+abstract class Cipher
+
+ # Encrypted data
+ var ciphertext = new Bytes.empty is writable
+
+ # Unencrypted data
+ var plaintext = new Bytes.empty is writable
+
+ # Encrypt plaintext and populate `self.ciphertext`
+ fun encrypt is abstract
+
+ # Decrypt ciphertext and populate `self.plaintext`
+ fun decrypt is abstract
+
+end
+
+# Simple XOR cipher where the whole plaintext is XORed with a single byte.
+class SingleByteXorCipher
+ super Cipher
+
+ # Cryptographic key used in encryption and decryption.
+ var key: Byte = 0.to_b
+
+ redef fun encrypt do
+ var key_bytes = new Bytes.with_capacity(1)
+ key_bytes.add(key)
+ ciphertext = plaintext.xorcipher(key_bytes)
+ end
+
+ redef fun decrypt do
+ var key_bytes = new Bytes.with_capacity(1)
+ key_bytes.add(key)
+ plaintext = ciphertext.xorcipher(key_bytes)
+ end
+end
+
+# XOR cipher where the key is repeated to match the length of the message.
+class RepeatingKeyXorCipher
+ super Cipher
+
+ # Cryptographic key used in encryption and decryption.
+ var key = new Bytes.empty
+
+ redef fun encrypt do
+ assert key.length > 0
+ ciphertext = plaintext.xorcipher(key)
+ end
+
+ redef fun decrypt do
+ assert key.length > 0
+ plaintext = ciphertext.xorcipher(key)
+ end
+end
yaw = 0.0
roll = 0.0
end
+
+ # Convert the position `x, y` on screen, to world coordinates on the plane at `target_z`
+ #
+ # `target_z` defaults to `0.0` and specifies the Z coordinates of the plane
+ # on which to project the screen position `x, y`.
+ #
+ # This method assumes that the camera is looking along the Z axis towards higher values.
+ # Using it in a different orientation can be useful, but won't result in valid
+ # world coordinates.
+ fun camera_to_world(x, y: Numeric, target_z: nullable Float): Point[Float]
+ do
+ # TODO, this method could be tweaked to support projecting the 2D point,
+ # on the near plane (x,y) onto a given distance no matter to orientation
+ # of the camera.
+
+ target_z = target_z or else 0.0
+
+ # Convert from pixel units / window resolution to
+ # units on the near clipping wall to
+ # units on the target wall at Z = 0
+ var near_height = (field_of_view_y/2.0).tan * near
+ var cross_screen_to_near = near_height / (display.height.to_f/2.0)
+ var cross_near_to_target = (position.z - target_z) / near
+ var mod = cross_screen_to_near * cross_near_to_target * 1.72 # FIXME drop the magic number
+
+ var wx = position.x + (x.to_f-display.width.to_f/2.0) * mod
+ var wy = position.y - (y.to_f-display.height.to_f/2.0) * mod
+ return new Point[Float](wx, wy)
+ end
end
# Orthogonal camera to draw UI objects with services to work with screens of different sizes
private var frame_count = 0
# Deadline used to compute `current_fps`
- private var frame_count_deadline = 5
+ private var frame_count_deadline = 5.0
# Check and sleep to maintain a frame-rate bellow `maximum_fps`
#
# Is automatically called at the end of `full_frame`.
fun limit_fps
do
- var t = clock.total.sec
+ var t = clock.total
if t >= frame_count_deadline then
var cfps = frame_count.to_f / 5.0
self.current_fps = cfps
frame_count = 0
- frame_count_deadline = t + 5
+ frame_count_deadline = t + 5.0
end
frame_count += 1
private var frame_count = 0
# Deadline used to compute `current_fps`
- private var frame_count_deadline = 0
+ private var frame_count_deadline = 0.0
# Check and sleep to maitain a frame-rate bellow `maximum_fps`
# Also periodically uptate `current_fps`
# Is automatically called at the end of `full_frame`.
fun limit_fps
do
- var t = clock.total.sec
+ var t = clock.total
if t >= frame_count_deadline then
var cfps = frame_count.to_f / 5.0
self.current_fps = cfps
frame_count = 0
- frame_count_deadline = t + 5
+ frame_count_deadline = t + 5.0
end
frame_count += 1
A minimal example follows with a custom `Action` and using `FileServer`.
More general examples are available at `lib/nitcorn/examples/`.
-It includes the configuration of `http://xymus.net/` which merges many other _nitcorn_ applications.
+For an example of a larger project merging many _nitcorn_ applications into one server,
+take a look at the configuration of `http://xymus.net/` at `../contrib/xymus_net/xymus_net.nit`.
Larger projects using _nitcorn_ can be found in the `contrib/` folder:
* _opportunity_ is a meetup planner heavily based on _nitcorn_.
mkdir -p bin/
../../../bin/nitc --dir bin src/nitcorn_hello_world.nit src/simple_file_server.nit
-xymus.net:
- mkdir -p bin/
- ../../../bin/nitc --dir bin/ src/xymus_net.nit
-
pre-build: src/restful_annot_gen.nit
src/restful_annot_gen.nit:
../../../bin/nitrestful -o $@ src/restful_annot.nit
# Show directory listing?
var show_directory_listing = true is writable
+ # Default file returned when no static file matches the requested URI.
+ #
+ # If no `default_file` is provided, the FileServer responds 404 error to
+ # unmatched queries.
+ var default_file: nullable String = null is writable
+
redef fun answer(request, turi)
do
var response
# This make sure that the requested file is within the root folder.
if (local_file + "/").has_prefix(root) then
# Does it exists?
- if local_file.file_exists then
- if local_file.file_stat.is_dir then
+ var file_stat = local_file.file_stat
+ if file_stat != null then
+ if file_stat.is_dir then
# If we target a directory without an ending `/`,
# redirect to the directory ending with `/`.
- if not request.uri.is_empty and
- request.uri.chars.last != '/' then
- response = new HttpResponse(303)
- response.header["Location"] = request.uri + "/"
- return response
+ var uri = request.uri
+ if not uri.is_empty and uri.chars.last != '/' then
+ return answer_redirection(request.uri + "/")
end
# Show index file instead of the directory listing
end
end
- var is_dir = local_file.file_stat.is_dir
- if show_directory_listing and is_dir then
- # Show the directory listing
- var title = turi
- var files = local_file.files
+ file_stat = local_file.file_stat
+ if show_directory_listing and file_stat != null and file_stat.is_dir then
+ response = answer_directory_listing(request, turi, local_file)
+ else if file_stat != null and not file_stat.is_dir then # It's a single file
+ response = answer_file(local_file)
+ else response = answer_default
+ else response = answer_default
+ else response = new HttpResponse(403)
- alpha_comparator.sort files
+ if response.status_code != 200 then
+ var tmpl = error_page(response.status_code)
+ if header != null and tmpl isa ErrorTemplate then tmpl.header = header
+ response.body = tmpl.to_s
+ end
- var links = new Array[String]
- if turi.length > 1 then
- var path = (request.uri + "/..").simplify_path
- links.add "<a href=\"{path}/\">..</a>"
- end
- for file in files do
- var local_path = local_file.join_path(file).simplify_path
- var web_path = file.simplify_path
- if local_path.file_stat.is_dir then web_path = web_path + "/"
- links.add "<a href=\"{web_path}\">{file}</a>"
- end
+ return response
+ end
+
+ # Answer the `default_file` if any.
+ fun answer_default: HttpResponse do
+ var default_file = self.default_file
+ if default_file == null then
+ return new HttpResponse(404)
+ end
+
+ var local_file = (root / default_file).simplify_path
+ return answer_file(local_file)
+ end
- var header = self.header
- var header_code
- if header != null then
- header_code = header.write_to_string
- else header_code = ""
+ # Answer a 303 redirection to `location`.
+ fun answer_redirection(location: String): HttpResponse do
+ var response = new HttpResponse(303)
+ response.header["Location"] = location
+ return response
+ end
+
+ # Build a reponse containing a single `local_file`.
+ #
+ # Returns a 404 error if local_file does not exists.
+ fun answer_file(local_file: String): HttpResponse do
+ if not local_file.file_exists then return new HttpResponse(404)
+
+ var response = new HttpResponse(200)
+ response.files.add local_file
+
+ # Set Content-Type depending on the file extension
+ var ext = local_file.file_extension
+ if ext != null then
+ var media_type = media_types[ext]
+ if media_type != null then
+ response.header["Content-Type"] = media_type
+ else response.header["Content-Type"] = "application/octet-stream"
+ end
- response = new HttpResponse(200)
- response.body = """
+ # Cache control
+ response.header["cache-control"] = cache_control
+ return response
+ end
+
+ # Answer with a directory listing for files within `local_files`.
+ fun answer_directory_listing(request: HttpRequest, turi, local_file: String): HttpResponse do
+ # Show the directory listing
+ var title = turi
+ var files = local_file.files
+
+ alpha_comparator.sort files
+
+ var links = new Array[String]
+ if turi.length > 1 then
+ var path = (request.uri + "/..").simplify_path
+ links.add "<a href=\"{path}/\">..</a>"
+ end
+ for file in files do
+ var local_path = local_file.join_path(file).simplify_path
+ var web_path = file.simplify_path
+ var file_stat = local_path.file_stat
+ if file_stat != null and file_stat.is_dir then web_path = web_path + "/"
+ links.add "<a href=\"{web_path}\">{file}</a>"
+ end
+
+ var header = self.header
+ var header_code
+ if header != null then
+ header_code = header.write_to_string
+ else header_code = ""
+
+ var response = new HttpResponse(200)
+ response.body = """
<!DOCTYPE html>
<head>
<meta charset="utf-8">
</body>
</html>"""
- response.header["Content-Type"] = media_types["html"].as(not null)
- else if not is_dir then
- # It's a single file
- response = new HttpResponse(200)
- response.files.add local_file
-
- var ext = local_file.file_extension
- if ext != null then
- var media_type = media_types[ext]
- if media_type != null then
- response.header["Content-Type"] = media_type
- else response.header["Content-Type"] = "application/octet-stream"
- end
-
- # Cache control
- response.header["cache-control"] = cache_control
-
- else response = new HttpResponse(404)
- else response = new HttpResponse(404)
- else response = new HttpResponse(403)
-
- if response.status_code != 200 then
- var tmpl = error_page(response.status_code)
- if header != null and tmpl isa ErrorTemplate then tmpl.header = header
- response.body = tmpl.to_s
- end
-
+ response.header["Content-Type"] = media_types["html"].as(not null)
return response
end
end
return self & 0x3FFF_FFFF
end
end
+
+redef universal Float
+ # Smoothened `self`, used by `ImprovedNoise`
+ private fun fade: Float do return self*self*self*(self*(self*6.0-15.0)+10.0)
+end
+
+# Direct translation of Ken Perlin's improved noise Java implementation
+#
+# This implementation differs from `PerlinNoise` on two main points.
+# This noise is calculated for a 3D point, vs 2D in `PerlinNoise`.
+# `PerlinNoise` is based off a customizable seed, while this noise has a static data source.
+class ImprovedNoise
+
+ # Permutations
+ private var p: Array[Int] = [151,160,137,91,90,15,
+ 131,13,201,95,96,53,194,233,7,225,140,36,103,30,69,142,8,99,37,240,21,10,23,
+ 190, 6,148,247,120,234,75,0,26,197,62,94,252,219,203,117,35,11,32,57,177,33,
+ 88,237,149,56,87,174,20,125,136,171,168, 68,175,74,165,71,134,139,48,27,166,
+ 77,146,158,231,83,111,229,122,60,211,133,230,220,105,92,41,55,46,245,40,244,
+ 102,143,54, 65,25,63,161, 1,216,80,73,209,76,132,187,208, 89,18,169,200,196,
+ 135,130,116,188,159,86,164,100,109,198,173,186, 3,64,52,217,226,250,124,123,
+ 5,202,38,147,118,126,255,82,85,212,207,206,59,227,47,16,58,17,182,189,28,42,
+ 223,183,170,213,119,248,152, 2,44,154,163, 70,221,153,101,155,167, 43,172,9,
+ 129,22,39,253, 19,98,108,110,79,113,224,232,178,185, 112,104,218,246,97,228,
+ 251,34,242,193,238,210,144,12,191,179,162,241, 81,51,145,235,249,14,239,107,
+ 49,192,214, 31,181,199,106,157,184, 84,204,176,115,121,50,45,127, 4,150,254,
+ 138,236,205,93,222,114,67,29,24,72,243,141,128,195,78,66,215,61,156,180] * 2
+
+ # Noise value in [-1..1] at 3D coordinates `x, y, z`
+ fun noise(x, y, z: Float): Float
+ do
+ var xx = x.floor.to_i & 255
+ var yy = y.floor.to_i & 255
+ var zz = z.floor.to_i & 255
+
+ x -= x.floor
+ y -= y.floor
+ z -= z.floor
+
+ var u = x.fade
+ var v = y.fade
+ var w = z.fade
+
+ var a = p[xx ] + yy
+ var aa = p[a ] + zz
+ var ab = p[a+1 ] + zz
+ var b = p[xx+1] + yy
+ var ba = p[b ] + zz
+ var bb = p[b+1 ] + zz
+
+ return w.lerp(v.lerp(u.lerp(grad(p[aa ], x, y, z ),
+ grad(p[ba ], x-1.0, y, z )),
+ u.lerp(grad(p[ab ], x, y-1.0, z ),
+ grad(p[bb ], x-1.0, y-1.0, z ))),
+ v.lerp(u.lerp(grad(p[aa+1], x, y, z-1.0),
+ grad(p[ba+1], x-1.0, y, z-1.0)),
+ u.lerp(grad(p[ab+1], x, y-1.0, z-1.0),
+ grad(p[bb+1], x-1.0, y-1.0, z-1.0))))
+ end
+
+ # Value at a corner of the grid
+ private fun grad(hash: Int, x, y, z: Float): Float
+ do
+ var h = hash & 15
+ var u = if h < 8 then x else y
+ var v = if h < 4 then y else if h == 12 or h == 14 then x else z
+ return (if h.is_even then u else -u) + (if h & 2 == 0 then v else -v)
+ end
+end
# Total execution time of this event
var sum = 0.0
- # Register a new event execution time with a `Timespec`
- fun add(lapse: Timespec) do add_float lapse.to_f
-
- # Register a new event execution time in seconds using a `Float`
- fun add_float(time: Float)
+ # Register a new event execution time in seconds
+ fun add(time: Float)
do
if time.to_f < min.to_f or count == 0 then min = time
if time.to_f > max.to_f then max = time
If you run the app from another directory, it’s safer to use the absolute path of
the directory that you want to serve.
+In some cases, you can want to redirect request to static files to a default file
+instead of returning a 404 error.
+This can be achieved by specifying a default file in the StaticHandler:
+
+~~~
+app.use("/static/", new StaticHandler("public/", "default.html"))
+~~~
+
+This way all non-matched queries to the StaticHandler will be answered with the
+`default.html` file.
+
## Advanced Routing
**Routing** refers to the definition of application end points (URIs) and how
* `res.send()` Send a response of various types.
* `res.error()` Set the response status code and send its message as the response body.
+## Response cycle
+
+When the popcorn `App` receives a request, the response cycle is the following:
+
+1. `pre-middlewares` lookup matching middlewares registered with `use_before(pre_middleware)`:
+ 1. execute matching middleware by registration order
+ 2. if a middleware send a response then let the `pre-middlewares` loop continue
+ with the next middleware
+2. `response-handlers` lookup matching handlers registered with `use(handler)`:
+ 1. execute matching middleware by registration order
+ 2. if a middleware send a response then stop the `response-handlers` loop
+ 3. if no hander matches or sends a response, generate a 404 response
+3. `post-middlewares` lookup matching handlers registered with `use_after(post_handler)`:
+ 1. execute matching middleware by registration order
+ 2. if a middleware send a response then let the `post-middlewares` loop continue
+ with the next middleware
+
## Middlewares
### Overview
var app = new App
-app.use("/*", new MyLogger)
+app.use_before("/*", new MyLogger)
app.use("/", new HelloHandler)
app.listen("localhost", 3000)
~~~
(even 404 ones) pass through the middleware handler.
This handler just prints “Request Logged!” when a request is received.
-The order of middleware loading is important: middleware functions that are loaded first are also executed first.
-In the above example, `MyLogger` will be executed before `HelloHandler`.
+Be default, the order of middleware execution is that are loaded first are also executed first.
+To ensure our middleware `MyLogger` will be executed before all the other, we add it
+with the `use_before` method.
### Ultra cool, more advanced logger example
redef fun all(req, res) do
var timer = req.timer
if timer != null then
- print "{req.method} {req.uri} {res.color_status} ({timer.total})"
+ print "{req.method} {req.uri} {res.color_status} ({timer.total}s)"
else
print "{req.method} {req.uri} {res.color_status}"
end
end
var app = new App
-app.use("/*", new RequestTimeHandler)
+app.use_before("/*", new RequestTimeHandler)
app.use("/", new HelloHandler)
-app.use("/*", new LogHandler)
+app.use_after("/*", new LogHandler)
app.listen("localhost", 3000)
~~~
from the `req` parameter.
We use the new middleware called `RequestTimeHandler` to initialize the request timer.
+Because of the `use_before` method, the `RequestTimeHandler` middleware will be executed
+before all the others.
+
+We then let the `HelloHandler` produce the response.
Finally, our `LogHandler` will display a bunch of data and use the request `timer`
to display the time it took to process the request.
+Because of the `use_after` method, the `LogHandler` middleware will be executed after
+all the others.
The app now uses the `RequestTimeHandler` middleware for every requests received
by the Popcorn app.
import popcorn
var app = new App
-app.use("/*", new StaticHandler("my-ng-app/"))
+app.use("/*", new StaticHandler("my-ng-app/", "index.html"))
app.listen("localhost", 3000)
~~~
+Because the StaticHandler will not find the angular routes as static files,
+you must specify the path to the default angular controller.
+In this example, the StaticHandler will redirect any unknown requests to the `index.html`
+angular controller.
+
See the examples for a more detailed use case working with a JSON API.
var app = new App
app.use("/counter", new CounterAPI)
-app.use("/*", new StaticHandler("www/"))
+app.use("/*", new StaticHandler("www/", "index.html"))
app.listen("localhost", 3000)
redef fun all(req, res) do
var timer = req.timer
if timer != null then
- print "{req.method} {req.uri} {res.color_status} ({timer.total})"
+ print "{req.method} {req.uri} {res.color_status} ({timer.total}s)"
else
print "{req.method} {req.uri} {res.color_status}"
end
end
var app = new App
-app.use("/*", new RequestTimeHandler)
+app.use_before("/*", new RequestTimeHandler)
app.use("/", new HelloHandler)
-app.use("/*", new LogHandler)
+app.use_after("/*", new LogHandler)
app.listen("localhost", 3000)
var app = new App
-app.use("/*", new LogHandler)
+app.use_before("/*", new LogHandler)
app.use("/", new HelloHandler)
app.listen("localhost", 3000)
--- /dev/null
+# This file is part of NIT ( http://www.nitlanguage.org ).
+#
+# Copyright 2016 Alexandre Terrasa <alexandre@moz-code.org>
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+
+import popcorn
+
+var app = new App
+app.use("/", new StaticHandler("public/", "default.html"))
+app.listen("localhost", 3000)
--- /dev/null
+<!DOCTYPE html>
+<html>
+ <head>
+ <meta charset="UTF-8">
+
+ <title>Some Popcorn love</title>
+
+ <link rel="stylesheet" type="text/css" href="/css/style.css">
+ </head>
+ <body>
+ <h1>Default Page</h1>
+ </body>
+</html>
# Static files directory to serve.
var static_dir: String
+ # Default file to serve if nothing matches the request.
+ #
+ # `null` for no default file.
+ var default_file: nullable String
+
# Internal file server used to lookup and render files.
var file_server: FileServer is lazy do
var srv = new FileServer(static_dir)
srv.show_directory_listing = false
+ srv.default_file = default_file
return srv
end
# List of handlers to match with requests.
private var handlers = new Map[AppRoute, Handler]
+ # List of handlers to match before every other.
+ private var pre_handlers = new Map[AppRoute, Handler]
+
+ # List of handlers to match after every other.
+ private var post_handlers = new Map[AppRoute, Handler]
+
# Register a `handler` for a route `path`.
#
# Route paths are matched in registration order.
fun use(path: String, handler: Handler) do
- var route
- if handler isa Router or handler isa StaticHandler then
- route = new AppGlobRoute(path)
- else if path.has_suffix("*") then
- route = new AppGlobRoute(path)
- else
- route = new AppParamRoute(path)
- end
+ var route = build_route(handler, path)
handlers[route] = handler
end
+ # Register a pre-handler for a route `path`.
+ #
+ # Prehandlers are matched before every other handlers in registrastion order.
+ fun use_before(path: String, handler: Handler) do
+ var route = build_route(handler, path)
+ pre_handlers[route] = handler
+ end
+
+ # Register a post-handler for a route `path`.
+ #
+ # Posthandlers are matched after every other handlers in registrastion order.
+ fun use_after(path: String, handler: Handler) do
+ var route = build_route(handler, path)
+ post_handlers[route] = handler
+ end
+
redef fun handle(route, uri, req, res) do
if not route.match(uri) then return
+ handle_pre(route, uri, req, res)
+ handle_in(route, uri, req, res)
+ handle_post(route, uri, req, res)
+ end
+
+ private fun handle_pre(route: AppRoute, uri: String, req: HttpRequest, res: HttpResponse) do
+ for hroute, handler in pre_handlers do
+ handler.handle(hroute, route.uri_root(uri), req, res)
+ end
+ end
+
+ private fun handle_in(route: AppRoute, uri: String, req: HttpRequest, res: HttpResponse) do
for hroute, handler in handlers do
handler.handle(hroute, route.uri_root(uri), req, res)
if res.sent then break
end
end
+
+ private fun handle_post(route: AppRoute, uri: String, req: HttpRequest, res: HttpResponse) do
+ for hroute, handler in post_handlers do
+ handler.handle(hroute, route.uri_root(uri), req, res)
+ end
+ end
+
+ private fun build_route(handler: Handler, path: String): AppRoute do
+ if handler isa Router or handler isa StaticHandler then
+ return new AppGlobRoute(path)
+ else if path.has_suffix("*") then
+ return new AppGlobRoute(path)
+ else
+ return new AppParamRoute(path)
+ end
+ end
end
# Popcorn application.
redef fun all(req, res) do
var clock = req.clock
if clock != null then
- print "{req.method} {req.uri} {status(res)} ({clock.total})"
+ print "{req.method} {req.uri} {status(res)} ({clock.total}s)"
else
print "{req.method} {req.uri} {status(res)}"
end
redef fun answer(req, uri) do
uri = uri.simplify_path
var res = new HttpResponse(404)
+ for route, handler in pre_handlers do
+ handler.handle(route, uri, req, res)
+ end
for route, handler in handlers do
handler.handle(route, uri, req, res)
+ if res.sent then break
end
if not res.sent then
res.send(error_tpl(res.status_code, res.status_message), 404)
end
+ for route, handler in post_handlers do
+ handler.handle(route, uri, req, res)
+ end
res.session = req.session
return res
end
[Client] curl -s localhost:*****/counter -X POST
{"label":"Visitors","value":1}
[Client] curl -s localhost:*****/counter
-{"label":"Visitors","value":1}
\ No newline at end of file
+{"label":"Visitors","value":1}
+[Client] curl -s localhost:*****/not_found
+<!DOCTYPE html>
+<html lang='en' ng-app='ng-example'>
+ <head>
+ <base href='/'>
+ <title>ng-example</title>
+ </head>
+ <body>
+ <div ng-view></div>
+
+ <script src='https://cdnjs.cloudflare.com/ajax/libs/angular.js/1.5.5/angular.min.js'></script>
+ <script src='https://cdnjs.cloudflare.com/ajax/libs/angular.js/1.5.5/angular-route.js'></script>
+ <script src='/javascripts/ng-example.js'></script>
+ </body>
+</html>
--- /dev/null
+
+[Client] curl -s localhost:*****/css/style.css
+body {
+ color: blue;
+ padding: 20px;
+}
+
+[Client] curl -s localhost:*****/js/app.js
+alert("Hello World!");
+
+[Client] curl -s localhost:*****/hello.html
+<!DOCTYPE html>
+<html>
+ <head>
+ <meta charset="UTF-8">
+
+ <title>Some Popcorn love</title>
+
+ <link rel="stylesheet" type="text/css" href="/css/style.css">
+ </head>
+ <body>
+ <h1>Hello Popcorn!</h1>
+
+ <img src="/images/trollface.jpg" alt="maybe it's a kitten?" />
+
+ <script src="/js/app.js"></script>
+ </body>
+</html>
+
+[Client] curl -s localhost:*****/
+<!DOCTYPE html>
+<html>
+ <head>
+ <meta charset="UTF-8">
+
+ <title>Some Popcorn love</title>
+
+ <link rel="stylesheet" type="text/css" href="/css/style.css">
+ </head>
+ <body>
+ <h1>Default Page</h1>
+ </body>
+</html>
+
+[Client] curl -s localhost:*****/css/not_found.nit
+<!DOCTYPE html>
+<html>
+ <head>
+ <meta charset="UTF-8">
+
+ <title>Some Popcorn love</title>
+
+ <link rel="stylesheet" type="text/css" href="/css/style.css">
+ </head>
+ <body>
+ <h1>Default Page</h1>
+ </body>
+</html>
+
+[Client] curl -s localhost:*****/static/css/not_found.nit
+<!DOCTYPE html>
+<html>
+ <head>
+ <meta charset="UTF-8">
+
+ <title>Some Popcorn love</title>
+
+ <link rel="stylesheet" type="text/css" href="/css/style.css">
+ </head>
+ <body>
+ <h1>Default Page</h1>
+ </body>
+</html>
+
+[Client] curl -s localhost:*****/not_found.nit
+<!DOCTYPE html>
+<html>
+ <head>
+ <meta charset="UTF-8">
+
+ <title>Some Popcorn love</title>
+
+ <link rel="stylesheet" type="text/css" href="/css/style.css">
+ </head>
+ <body>
+ <h1>Default Page</h1>
+ </body>
+</html>
</html>
[Client] curl -s localhost:*****/
-Warning: Headers already sent!
-<!DOCTYPE html>
-<html>
- <body>
- <h1>Another Index</h1>
- </body>
-</html>
<!DOCTYPE html>
<html>
<body>
end
var app = new App
-app.use("/*", new RequestTimeHandler)
+app.use_before("/*", new RequestTimeHandler)
app.use("/", new HelloHandler)
-app.use("/*", new LogHandler)
+app.use_after("/*", new LogHandler)
var host = test_host
var port = test_port
system "curl -s {host}:{port}/counter"
system "curl -s {host}:{port}/counter -X POST"
system "curl -s {host}:{port}/counter"
+ system "curl -s {host}:{port}/not_found" # handled by angular controller
return null
end
end
var app = new App
app.use("/counter", new CounterAPI)
-app.use("/*", new StaticHandler("www/"))
+app.use("/*", new StaticHandler("../examples/angular/www/", "index.html"))
var host = test_host
var port = test_port
end
var app = new App
-app.use("/*", new LogHandler)
+app.use_before("/*", new LogHandler)
app.use("/", new HelloHandler)
var host = test_host
--- /dev/null
+# This file is part of NIT ( http://www.nitlanguage.org ).
+#
+# Copyright 2016 Alexandre Terrasa <alexandre@moz-code.org>
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+
+import base_tests
+import example_static_default
+
+class TestClient
+ super ClientThread
+
+ redef fun main do
+ system "curl -s {host}:{port}/css/style.css"
+ system "curl -s {host}:{port}/js/app.js"
+ system "curl -s {host}:{port}/hello.html"
+ system "curl -s {host}:{port}/"
+
+ system "curl -s {host}:{port}/css/not_found.nit"
+ system "curl -s {host}:{port}/static/css/not_found.nit"
+ system "curl -s {host}:{port}/not_found.nit"
+
+ return null
+ end
+end
+
+var app = new App
+app.use("/", new StaticHandler("../examples/static_files/public/", "default.html"))
+
+var host = test_host
+var port = test_port
+
+var server = new AppThread(host, port, app)
+server.start
+0.1.sleep
+
+var client = new TestClient(host, port)
+client.start
+client.join
+0.1.sleep
+
+exit 0
# See the License for the specific language governing permissions and
# limitations under the License.
+# A native wrapper ove the postgres c api
module native_postgres is pkgconfig("libpq")
in "C header" `{
new nonfatal_error `{ return PGRES_NONFATAL_ERROR; `}
new fatal_error `{ return PGRES_FATAL_ERROR; `}
- fun is_ok: Bool `{return self == PGRES_TUPLES_OK || self == PGRES_COMMAND_OK; `}
+ fun is_ok: Bool `{
+ return !(self == PGRES_BAD_RESPONSE || self == PGRES_NONFATAL_ERROR || self == PGRES_FATAL_ERROR);
+ `}
redef fun to_s import NativeString.to_s `{
char * err = PQresStatus(self);
fun is_ok: Bool `{return self == CONNECTION_OK; `}
end
-extern class PGResult `{PGresult *`}
+extern class NativePGResult `{PGresult *`}
# Frees the memory block associated with the result
fun clear `{PQclear(self); `}
extern class NativePostgres `{PGconn *`}
# Connect to a new database using the conninfo string as a parameter
- new connectdb(conninfo: String) import String.to_cstring `{
+ new connectdb(conninfo: Text) import Text.to_cstring `{
PGconn * self = NULL;
- self = PQconnectdb(String_to_cstring(conninfo));
+ self = PQconnectdb(Text_to_cstring(conninfo));
return self;
`}
# Submits a query to the server and waits for the result returns the ExecStatustype of the query
- fun exec(query: String): PGResult import String.to_cstring `{
- PGresult *res = PQexec(self, String_to_cstring(query));
+ fun exec(query: Text): NativePGResult import Text.to_cstring `{
+ PGresult *res = PQexec(self, Text_to_cstring(query));
return res;
`}
# Prepares a statement with the given parameters
- fun prepare(stmt: String, query: String, nParams: Int):PGResult import String.to_cstring `{
+ fun prepare(stmt: String, query: String, nParams: Int): NativePGResult import String.to_cstring `{
const char * stmtName = String_to_cstring(stmt);
const char * queryStr = String_to_cstring(query);
PGresult * res = PQprepare(self, stmtName, queryStr, nParams, NULL);
return res;
`}
- fun exec_prepared(stmt: String, nParams: Int, values: Array[String], pLengths: Array[Int], pFormats: Array[Int], resultFormat: Int):PGResult import String.to_cstring, Array[String].[], Array[Int].[] `{
+ fun exec_prepared(stmt: String, nParams: Int, values: Array[String], pLengths: Array[Int], pFormats: Array[Int], resultFormat: Int): NativePGResult import String.to_cstring, Array[String].[], Array[Int].[] `{
const char * stmtName = String_to_cstring(stmt);
const char * paramValues[nParams];
int paramLengths[nParams];
--- /dev/null
+# This file is part of NIT ( http://www.nitlanguage.org ).
+#
+# Copyright 2016 Guilherme Mansur<guilhermerpmansur@gmail.com>
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+
+# Services to manipulate a Postgres database
+#
+# For more information, refer to the documentation of http://www.postgresql.org/docs/manuals/
+#
+# ### Usage example
+#
+# ~~~
+# class Animal
+# var name: String
+# var kind: String
+# var age: Int
+# end
+#
+# var animals = new Array[Animal]
+# var dog = new Animal("Lassy", "dog", 10)
+# var cat = new Animal("Garfield", "cat", 3)
+# var turtle = new Animal("George", "turtle", 123)
+#
+# animals.add(dog)
+# animals.add(cat)
+# animals.add(turtle)
+#
+# var db = new Postgres.open("dbname=postgres")
+#
+# assert db_is_open: not db.is_closed
+# assert create_table: db.create_table("IF NOT EXISTS animals (aname TEXT PRIMARY KEY, kind TEXT NOT NULL, age INT NOT NULL)") else print db.error
+#
+# for animal in animals do
+# assert insert: db.insert("INTO animals VALUES('{animal.name}', '{animal.kind}', {animal.age})") else print db.error
+# end
+#
+# var result = db.raw_execute("SELECT * FROM animals")
+# assert result.is_ok
+# assert drop_table: db.execute("DROP TABLE animals")
+# db.finish
+# assert db_is_closed: db.is_closed
+# ~~~
+module postgres
+
+private import native_postgres
+
+# A connection to a Postgres database
+class Postgres
+ private var native_connection: NativePostgres
+
+ var is_closed = true
+
+ # Open the connnection with the database using the `conninfo`
+ init open(conninfo: Text)
+ do
+ init(new NativePostgres.connectdb(conninfo))
+ if native_connection.status.is_ok then is_closed = false
+ end
+
+ # Close this connection with the database
+ fun finish
+ do
+ if is_closed then return
+
+ is_closed = true
+
+ native_connection.finish
+ end
+
+ fun prepare(stmt_name:String, query:String, num_params: Int):PGResult do return new PGResult(native_connection.prepare(stmt_name, query, num_params))
+
+ fun exec_prepared(stmt_name: String, num_params: Int, values: Array[String], param_lengths: Array[Int], param_formats: Array[Int], result_format: Int):PGResult do
+ return new PGResult(native_connection.exec_prepared(stmt_name, num_params, values, param_lengths, param_formats, result_format))
+ end
+
+ # Executes a `query` and returns the raw `PGResult`
+ fun raw_execute(query: Text): PGResult do return new PGResult(native_connection.exec(query))
+
+ # Execute the `sql` statement and returns `true` on success
+ fun execute(query: Text): Bool do return native_connection.exec(query).status.is_ok
+
+ # Create a table on the DB with a statement beginning with "CREATE TABLE ", followed by `rest`
+ #
+ # This method does not escape special characters.
+ fun create_table(rest: Text): Bool do return execute("CREATE TABLE " + rest)
+
+ # Insert in the DB with a statement beginning with "INSERT ", followed by `rest`
+ #
+ # This method does not escape special characters.
+ fun insert(rest: Text): Bool do return execute("INSERT " + rest)
+
+ # Replace in the DB with a statement beginning with "REPLACE", followed by `rest`
+ #
+ # This method does not escape special characters.
+ fun replace(rest: Text): Bool do return execute("REPLACE " + rest)
+
+ # The latest error message on the connection an empty string if none
+ fun error: String do return native_connection.error
+
+ # The status of this connection
+ fun is_valid: Bool do return native_connection.status.is_ok
+
+ # Resets the connection to the database
+ fun reset do native_connection.reset
+end
+
+# The result of a given query
+class PGResult
+ private var pg_result: NativePGResult
+
+ fun clear do pg_result.clear
+
+ # Returns the number of rows in the query result
+ fun ntuples:Int do return pg_result.ntuples
+
+ # Returns the number of columns in each row of the query result
+ fun nfields:Int do return pg_result.nfields
+
+ # Returns the ExecStatusType of a result
+ fun is_ok:Bool do return pg_result.status.is_ok
+
+ # Returns the field name of a given `column_number`
+ fun fname(column_number:Int):String do return pg_result.fname(column_number)
+
+ # Returns the column number associated with the `column_name`
+ fun fnumber(column_name:String):Int do return pg_result.fnumber(column_name)
+
+ # Returns a single field value of one row of the result at `row_number`, `column_number`
+ fun value(row_number:Int, column_number:Int):String do return pg_result.value(row_number, column_number)
+
+ # Tests wether a field specified by the `row_number` and `column_number` is null.
+ fun is_null(row_number:Int, column_number: Int): Bool do return pg_result.is_null(row_number, column_number)
+end
--- /dev/null
+[package]
+name=readline
+tags=lib
+maintainer=Frédéric Vachon <fredvac@gmail.com>
+license=Apache-2.0
+[upstream]
+browse=https://github.com/nitlang/nit/tree/master/lib/readline.nit
+git=https://github.com/nitlang/nit.git
+git.directory=lib/readline.nit
+homepage=http://nitlanguage.org
+issues=https://github.com/nitlang/nit/issues
--- /dev/null
+# This file is part of NIT (http://www.nitlanguage.org).
+#
+# Copyright 2016 Frédéric Vachon <fredvac@gmail.com>
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+
+# GNU readline library wrapper
+module readline is ldflags "-lreadline"
+
+in "C" `{
+ #include <readline/readline.h>
+ #include <readline/history.h>
+`}
+
+private fun native_readline(prompt: NativeString): NativeString `{
+ return readline(prompt);
+`}
+
+private fun native_add_history(data: NativeString) `{
+ if (data == NULL) return;
+ add_history(data);
+`}
+
+# Set emacs keybindings mode
+fun set_vi_mode `{ rl_editing_mode = 0; `}
+
+# Set emacs keybindings mode
+fun set_emacs_mode `{ rl_editing_mode = 1; `}
+
+# Use the GNU Library readline function
+# Returns `null` if EOF is read
+# If `with_history` is true, it will save all commands in the history except
+# empty strings and white characters strings
+fun readline(message: String, with_history: nullable Bool): nullable String do
+ var line = native_readline(message.to_cstring)
+ if line.address_is_null then return null
+
+ var nit_str = line.to_s
+
+ if with_history != null and with_history then
+ if nit_str.trim != "" then native_add_history(line)
+ end
+
+ return nit_str
+end
+
+# Adds the data String to the history no matter what it contains
+fun add_history(data: String) do native_add_history data.to_cstring
clock_gettime(CLOCK_MONOTONIC, self);
`}
- # Substract a Timespec from `self`.
- fun - ( o : Timespec ) : Timespec
+ # Subtract `other` from `self`
+ fun -(other: Timespec): Timespec
do
- var s = sec - o.sec
- var ns = nanosec - o.nanosec
- if ns > nanosec then s += 1
- return new Timespec( s, ns )
+ var s = sec - other.sec
+ var ns = nanosec - other.nanosec
+ if ns < 0 then
+ s -= 1
+ ns += 1000000000
+ end
+ return new Timespec(s, ns)
end
# Number of whole seconds of elapsed time.
end
# Keeps track of real time
+#
+# ~~~
+# var clock = new Clock
+#
+# # sleeping at least 1s
+# 1.0.sleep
+# assert clock.total >= 1.0
+# assert clock.lapse >= 1.0
+#
+# # sleeping at least 5ms
+# 0.005.sleep
+# assert clock.total >= 1.005
+# assert clock.lapse >= 0.005
+# ~~~
class Clock
- # Time at instanciation
+ super FinalizableOnce
+
+ # TODO use less mallocs
+
+ # Time at creation
protected var time_at_beginning = new Timespec.monotonic_now
# Time at last time a lapse method was called
protected var time_at_last_lapse = new Timespec.monotonic_now
# Smallest time frame reported by clock
- fun resolution : Timespec `{
+ fun resolution: Timespec `{
struct timespec* tv = malloc( sizeof(struct timespec) );
#ifdef __MACH__
clock_serv_t cclock;
return tv;
`}
- # Return timelapse since instanciation of this instance
- fun total : Timespec
+ # Seconds since the creation of this instance
+ fun total: Float
do
- return new Timespec.monotonic_now - time_at_beginning
+ var now = new Timespec.monotonic_now
+ var diff = now - time_at_beginning
+ var r = diff.to_f
+ diff.free
+ now.free
+ return r
end
- # Return timelapse since last call to lapse
- fun lapse : Timespec
+ # Seconds since the last call to `lapse`
+ fun lapse: Float
do
var nt = new Timespec.monotonic_now
var dt = nt - time_at_last_lapse
+ var r = dt.to_f
+ dt.free
+ time_at_last_lapse.free
time_at_last_lapse = nt
- return dt
+ return r
+ end
+
+ # Seconds since the last call to `lapse`, without resetting the lapse counter
+ fun peek_lapse: Float
+ do
+ var nt = new Timespec.monotonic_now
+ var dt = nt - time_at_last_lapse
+ var r = dt.to_f
+ nt.free
+ dt.free
+ return r
+ end
+
+ redef fun finalize_once
+ do
+ time_at_beginning.free
+ time_at_last_lapse.free
end
end
# then using a reference.
class SerializerCache
# Map of already serialized objects to the reference id
- private var sent: Map[Serializable, Int] = new StrictHashMap[Serializable, Int]
+ protected var sent: Map[Serializable, Int] = new StrictHashMap[Serializable, Int]
# Is `object` known?
fun has_object(object: Serializable): Bool do return sent.keys.has(object)
# Used by `Deserializer` to find already deserialized objects by their reference.
class DeserializerCache
# Map of references to already deserialized objects.
- private var received: Map[Int, Object] = new StrictHashMap[Int, Object]
+ protected var received: Map[Int, Object] = new StrictHashMap[Int, Object]
# Is there an object associated to `id`?
fun has_id(id: Int): Bool do return received.keys.has(id)
### `--no-shortcut-equal`
Always call == in a polymorphic way.
-### `--no-tag-primitive`
+### `--no-tag-primitives`
Use only boxes for primitive types.
The separate compiler uses tagged values to encode common primitive types like Int, Bool and Char.
Just add the trampolines of `--substitute-monomorph` without doing any additionnal optimizations.
-### `--no-tag-primitives`
-Use only boxes for primitive types.
-
## INTERNAL OPTIONS
These options can be used to control the fine behavior of the tool.
## CUSTOMIZATION
-### `--sharedir`
-Directory containing nitdoc assets.
+### `--share-dir`
+Directory containing tools assets.
By default `$NIT_DIR/share/nitdoc/` is used.
`nitunit` produces a XML file compatible with JUnit.
### `--dir`
-Working directory (default is '.nitunit').
+Working directory (default is 'nitunit.out').
In order to execute the tests, nit files are generated then compiled and executed in the giver working directory.
+In case of success, the directory is removed.
+In case of failure, it is kept as is so files can be investigated.
+
### `--nitc`
nitc compiler to use.
Indicate the specific Nit compiler executable to use. See `--nitc`.
+### `NIT_TESTING`
+
+The environment variable `NIT_TESTING` is set to `true` during the execution of program tests.
+Some libraries of programs can use it to produce specific reproducible results; or just to exit their executions.
+
+Unit-tests may unset this environment variable to retrieve the original behavior of such piece of software.
+
+### `SRAND`
+
+In order to maximize reproducibility, `SRAND` is set to 0.
+This make the pseudo-random generator no random at all.
+See `Sys::srand` for details.
+
+To retrieve the randomness, unit-tests may unset this environment variable then call `srand`.
+
+### `NIT_TESTING_ID`
+
+Parallel executions can cause some race collisions on named resources (e.g. DB table names).
+To solve this issue, `NIT_TESTING_ID` is initialized with a distinct integer identifier that can be used to give unique names to resources.
+
+Note: `rand` is not a recommended way to get a distinct identifier because its randomness is disabled by default. See `SRAND`.
+
+
# SEE ALSO
The Nit language documentation and the source code of its tools and libraries may be downloaded from <http://nitlanguage.org>
--- /dev/null
+<div class='card'>
+ <div class='card-left text-center'>
+ <entity-tag mentity='mentity' />
+ </div>
+ <div class='card-body'>
+ <h5 class='card-heading'>
+ <entity-signature mentity='mentity'/>
+ </h5>
+ <span class='synopsis' ng-bind-html='mentity.mdoc.html_synopsis' />
+ </div>
+</div>
--- /dev/null
+<div class='card' ng-if='mentity.mdoc'>
+ <div class='card-body'>
+ <div ng-bind-html='mentity.mdoc.html_documentation'></div>
+ </div>
+</div>
--- /dev/null
+<span>
+ <a ng-href='{{mentity.web_url}}'>{{mentity.name}}</a>
+</span>
--- /dev/null
+<div class='entity-list'
+ ng-if='(listEntities | filter:listObjectFilter).length > 0'>
+ <h3 id={{listId}}>
+ <span>{{listTitle}}</span>
+ <button class='btn btn-link btn-xs pull-right btn-filter' ng-click='toggleFilters()'>
+ <span class='glyphicon glyphicon-filter text-muted' />
+ </button>
+ </h3>
+ <div ng-if='showFilters'>
+ <ui-filter-form
+ search-filter='listObjectFilter'
+ visibility-filter='visibilityFilter'>
+ </div>
+ <div class='card-list'>
+ <entity-card mentity='mentity'
+ ng-repeat='mentity in listEntities | filter:listObjectFilter | visibility:visibilityFilter' />
+ </div>
+ </div>
+</div>
--- /dev/null
+<span ng-if='mentity.location'>
+ <a ng-href="{{mentity.web_url}}">{{mentity.location.file}}
+ <span ng-if='mentity.location.line_start'>:{{mentity.location.line_start}}</span>
+ </a>
+</span>
--- /dev/null
+<span class='signature'>
+ <span ng-repeat='modifier in mentity.modifiers'>
+ <span ng-if='modifier != "public"' class='modifier'>{{modifier}}</span>
+ </span>
+ <span class='name'>
+ <entity-link mentity='mentity' />
+ </span>
+ <span ng-if='mentity.mparameters'>
+ <span ng-if='mentity.mparameters.length > 0'>
+ <span>[</span>
+ <span ng-repeat='mparam in mentity.mparameters'>
+ <span>
+ <span>{{mparam.name}}</span>
+ <span>: </span>
+ <entity-signature mentity='mparam.mtype' />
+ </span>
+ <span ng-if='$middle'>, </span>
+ </span>
+ <span>]</span>
+ </span>
+ </span>
+ <span ng-if='mentity.msignature'>
+ <span ng-if='mentity.msignature.arity > 0'>
+ <span>(</span>
+ <span ng-repeat='mparam in mentity.msignature.mparams'>
+ <span>
+ <span>{{mparam.name}}</span>
+ <span ng-if='mentity.is_intro !== false'>
+ <span>: </span>
+ <entity-signature mentity='mparam.mtype' />
+ </span>
+ <span ng-if='mparam.is_vararg'>...</span>
+ </span>
+ <span ng-if='!first && !$last'>, </span>
+ </span>
+ <span>)</span>
+ </span>
+ <span ng-if='mentity.is_intro !== false && mentity.msignature.return_mtype'>
+ <span>: </span>
+ <entity-signature mentity='mentity.msignature.return_mtype' />
+ </span>
+ </span>
+ <span ng-if='mentity.is_intro !== false && mentity.static_mtype'>
+ <span>: </span>
+ <entity-signature mentity='mentity.static_mtype' />
+ </span>
+ <span ng-if='mentity.bound'>
+ <span>: </span>
+ <entity-signature mentity='mentity.bound' />
+ </span>
+</span>
--- /dev/null
+<span class="glyphicon glyphicon-tag" ng-class='{
+ "text-success": mentity.visibility == "public",
+ "text-warning": mentity.visibility == "protected",
+ "text-danger": mentity.visibility == "private",
+}' />
--- /dev/null
+<div class='media'>
+ <div class='media-left text-center' ng-if='mentity.visibility' ng-class='{
+ "text-success": mentity.visibility == "public",
+ "text-warning": mentity.visibility == "protected",
+ "text-danger": mentity.visibility == "private",
+ }'>
+ <span class="glyphicon glyphicon-tag"></span>
+ </div>
+ <div class='media-body'>
+ <h5 class='media-heading'>
+ <entity-signature mentity='mentity'/>
+ </h5>
+ <span class='synopsis'>{{mentity.mdoc.synopsis}}</span>
+ <div ng-if='recursive && mentity.mgroups'>
+ <group-block mentity-id='mgroup' ng-repeat='mgroup in mentity.mgroups' />
+ </div>
+ <div ng-if='recursive && mentity.mmodules'>
+ <module-block mentity-id='mmodule' ng-repeat='mmodule in mentity.mmodules' />
+ </div>
+ </div>
+</div>
--- /dev/null
+<button
+ class='btn btn-link btn-xs'
+ ng-click='toggle()'>
+ <span ng-if='property' ng-class='classesOn'/>
+ <span ng-if='!property' ng-class='classesOff'/>
+</button>
--- /dev/null
+<div class='form-group has-icon'>
+ <input type='text' class='form-control' ng-model='property' placeholder='Filter...'>
+ <span class='glyphicon glyphicon-search form-control-icon text-muted'></span>
+</div>
--- /dev/null
+<form class='form-inline'>
+ <ui-filter-field property='searchFilter.$' />
+ <div class='pull-right'>
+ <ui-filter-group-vis property='visibilityFilter' />
+ </div>
+</form>
--- /dev/null
+<div class='form-group'>
+ <ui-filter-button-vis property='property.public'
+ classes-on='"glyphicon glyphicon-eye-open text-success"'
+ classes-off='"glyphicon glyphicon-eye-close text-success"'
+ title='Toggle public' />
+ <ui-filter-button-vis property='property.protected'
+ classes-on='"glyphicon glyphicon-eye-open text-warning"'
+ classes-off='"glyphicon glyphicon-eye-close text-warning"'
+ title='Toggle protected' />
+ <ui-filter-button-vis property='property.private'
+ classes-on='"glyphicon glyphicon-eye-open text-danger"'
+ classes-off='"glyphicon glyphicon-eye-close text-danger"'
+ title='Toggle private' />
+</div>
--- /dev/null
+<!DOCTYPE html>
+<html lang='en' ng-app='nitweb'>
+ <head>
+ <base href='/'>
+ <meta charset='utf-8'>
+ <meta http-equiv='X-UA-Compatible' content='IE=edge'>
+ <meta name='viewport' content='width=device-width, initial-scale=1'>
+ <title>ng-doc</title>
+
+ <link href='https://maxcdn.bootstrapcdn.com/bootstrap/3.3.6/css/bootstrap.min.css'
+ integrity='sha384-1q8mTJOASx8j1Au+a5WDVnPi2lkFfwwEAa8hDDdjZlpLegxhjVME1fgjWPGmkzs7'
+ crossorigin='anonymous' rel='stylesheet'>
+
+ <link href='/stylesheets/nitweb_bootstrap.css' rel='stylesheet'>
+ <link href='/stylesheets/nitweb.css' rel='stylesheet'>
+ </head>
+ <body>
+ <nav class='navbar navbar-default navbar-fixed-top'>
+ <div class='container-fluid'>
+ <div class='col-xs-3 navbar-header'>
+ <a class='navbar-brand' ng-href='/'>Nitdoc</a>
+ </div>
+ </div>
+ </nav>
+ <div ng-view></div>
+
+ <script src='https://code.jquery.com/jquery-1.12.4.min.js'
+ integrity='sha256-ZosEbRLbNQzLpnKIkEdrPv7lOy9C27hHQ+Xp8a4MxAQ='
+ crossorigin='anonymous''></script>
+ <script src='https://maxcdn.bootstrapcdn.com/bootstrap/3.3.6/js/bootstrap.min.js'
+ integrity='sha384-0mSbJDEHialfmuBBQP6A4Qrprq5OVfW37PRR3j5ELqxss1yVqOtnepnHVP9aJ7xS'
+ crossorigin='anonymous'></script>
+ <script src='https://cdnjs.cloudflare.com/ajax/libs/angular.js/1.5.5/angular.min.js'>
+ </script>
+ <script src='https://cdnjs.cloudflare.com/ajax/libs/angular.js/1.5.5/angular-route.js'>
+ </script>
+ <script src='https://cdnjs.cloudflare.com/ajax/libs/angular.js/1.5.5/angular-sanitize.js'>
+ </script>
+
+ <script src='/javascripts/nitweb.js'></script>
+ <script src='/javascripts/model.js'></script>
+ <script src='/javascripts/entities.js'></script>
+ <script src='/javascripts/ui.js'></script>
+ </body>
+</html>
--- /dev/null
+/*
+ * Copyright 2016 Alexandre Terrasa <alexandre@moz-code.org>.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+(function() {
+ angular
+ .module('entities', ['ui', 'model'])
+
+ .controller('EntityCtrl', ['Model', '$routeParams', '$scope', function(Model, $routeParams, $scope) {
+ Model.loadEntity($routeParams.id,
+ function(data) {
+ $scope.mentity = data;
+ }, function(err) {
+ $scope.error = err;
+ });
+ }])
+
+ .directive('entityLink', function() {
+ return {
+ restrict: 'E',
+ scope: {
+ mentity: '='
+ },
+ templateUrl: '/directives/entity/link.html'
+ };
+ })
+
+ .directive('entityDoc', function() {
+ return {
+ restrict: 'E',
+ scope: {
+ mentity: '='
+ },
+ templateUrl: '/directives/entity/doc.html'
+ };
+ })
+
+ .directive('entitySignature', function() {
+ return {
+ restrict: 'E',
+ scope: {
+ mentity: '='
+ },
+ templateUrl: '/directives/entity/signature.html'
+ };
+ })
+
+ .directive('entityTag', function() {
+ return {
+ restrict: 'E',
+ scope: {
+ mentity: '='
+ },
+ replace: true,
+ templateUrl: '/directives/entity/tag.html'
+ };
+ })
+
+ .directive('entityLocation', function() {
+ return {
+ restrict: 'E',
+ scope: {
+ mentity: '='
+ },
+ templateUrl: '/directives/entity/location.html'
+ };
+ })
+
+ .directive('entityCard', function() {
+ return {
+ restrict: 'E',
+ scope: {
+ mentity: '='
+ },
+ replace: true,
+ templateUrl: '/directives/entity/card.html'
+ };
+ })
+
+ .directive('entityList', function() {
+ return {
+ restrict: 'E',
+ scope: {
+ listEntities: '=',
+ listTitle: '@',
+ listObjectFilter: '=',
+ },
+ templateUrl: '/directives/entity/list.html',
+ link: function ($scope, element, attrs) {
+ $scope.showFilters = false;
+ if(!$scope.listObjectFilter) {
+ $scope.listObjectFilter = {};
+ }
+ if(!$scope.visibilityFilter) {
+ $scope.visibilityFilter = {
+ public: true,
+ protected: true,
+ private: false
+ };
+ }
+ $scope.toggleFilters = function() {
+ $scope.showFilters = !$scope.showFilters;
+ };
+ }
+ };
+ })
+})();
--- /dev/null
+/*
+ * Copyright 2016 Alexandre Terrasa <alexandre@moz-code.org>.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+(function() {
+ var apiUrl = '/api';
+
+ angular
+ .module('model', [])
+
+ .factory('Model', [ '$http', function($http) {
+ return {
+ loadEntity: function(id, cb, cbErr) {
+ $http.get(apiUrl + '/entity/' + id)
+ .success(cb)
+ .error(cbErr);
+ }
+
+ };
+ }])
+})();
--- /dev/null
+/*
+ * Copyright 2016 Alexandre Terrasa <alexandre@moz-code.org>.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+(function() {
+ angular.module('nitweb', ['ngRoute', 'ngSanitize', 'entities'])
+
+ .config(function($routeProvider, $locationProvider) {
+ $routeProvider
+ .when('/', {
+ templateUrl: 'views/index.html'
+ })
+ .when('/package/:id', {
+ templateUrl: 'views/package.html',
+ controller: 'EntityCtrl',
+ controllerAs: 'entityCtrl'
+ })
+ .when('/group/:id', {
+ templateUrl: 'views/group.html',
+ controller: 'EntityCtrl',
+ controllerAs: 'entityCtrl'
+ })
+ .when('/module/:id', {
+ templateUrl: 'views/module.html',
+ controller: 'EntityCtrl',
+ controllerAs: 'entityCtrl'
+ })
+ .when('/class/:id', {
+ templateUrl: 'views/class.html',
+ controller: 'EntityCtrl',
+ controllerAs: 'entityCtrl'
+ })
+ .when('/classdef/:id', {
+ templateUrl: 'views/classdef.html',
+ controller: 'EntityCtrl',
+ controllerAs: 'entityCtrl'
+ })
+ .when('/property/:id', {
+ templateUrl: 'views/property.html',
+ controller: 'EntityCtrl',
+ controllerAs: 'entityCtrl'
+ })
+ .when('/propdef/:id', {
+ templateUrl: 'views/propdef.html',
+ controller: 'EntityCtrl',
+ controllerAs: 'entityCtrl'
+ })
+ .otherwise({
+ redirectTo: '/'
+ });
+ $locationProvider.html5Mode(true);
+ });
+})();
--- /dev/null
+/*
+ * Copyright 2016 Alexandre Terrasa <alexandre@moz-code.org>.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+(function() {
+ angular
+ .module('ui', [ 'model' ])
+
+ .directive('uiFilters', function() {
+ return {
+ restrict: 'E',
+ scope: {
+ property: '=',
+ classesOn: '=',
+ classesOff: '='
+ },
+ replace: true,
+ templateUrl: '/directives/ui-filter-button-vis.html',
+ link: function ($scope, element, attrs) {
+ $scope.toggle = function() {
+ $scope.property = !$scope.property;
+ }
+ }
+ };
+ })
+
+ .filter('visibility', function() {
+ return function(input, visibilityFilter) {
+ var res = [];
+ input.forEach(function(entry) {
+ if(visibilityFilter.public == false && entry.visibility == "public") {
+ return;
+ }
+ if(visibilityFilter.protected == false && entry.visibility == "protected") {
+ return;
+ }
+ if(visibilityFilter.private == false && entry.visibility == "private") {
+ return;
+ }
+ res.push(entry);
+ });
+ return res;
+ };
+ })
+
+ .directive('uiFilterForm', function() {
+ return {
+ restrict: 'E',
+ scope: {
+ searchFilter: '=',
+ visibilityFilter: '='
+ },
+ replace: true,
+ templateUrl: '/directives/ui-filter-form.html'
+ };
+ })
+
+ .directive('uiFilterField', function() {
+ return {
+ restrict: 'E',
+ scope: {
+ property: '='
+ },
+ replace: true,
+ templateUrl: '/directives/ui-filter-field.html'
+ };
+ })
+
+ .directive('uiFilterGroupVis', function() {
+ return {
+ restrict: 'E',
+ scope: {
+ property: '='
+ },
+ replace: true,
+ templateUrl: '/directives/ui-filter-group-vis.html'
+ };
+ })
+
+ .directive('uiFilterButtonVis', function() {
+ return {
+ restrict: 'E',
+ scope: {
+ property: '=',
+ classesOn: '=',
+ classesOff: '='
+ },
+ replace: true,
+ templateUrl: '/directives/ui-filter-button-vis.html',
+ link: function ($scope, element, attrs) {
+ $scope.toggle = function() {
+ $scope.property = !$scope.property;
+ }
+ }
+ };
+ })
+})();
--- /dev/null
+/* Body */
+
+body {
+ background: #f2f2f2;
+ margin-top: 70px;
+ margin-bottom: 70px;
+}
+
+h1, h2, h3, h4, h5, h6 {
+ color: #666;
+}
+
+a {
+ cursor: pointer;
+}
+
+.nitdoc h1, .nitdoc h2, .nitdoc h3, .nitdoc h4, .nitdoc h5, .nitdoc h6 {
+ color: #333;
+}
+
+.page-header {
+ margin-top: 0;
+ border: none;
+}
+
+/* cards */
+
+.card.active {
+ border: 1px solid #1E9431;
+}
+
+.card, .card-body { overflow: hidden; }
+
+.card-heading {
+ margin-top: 0;
+ margin-bottom: 5px;
+}
+
+.card {
+ background: #fff;
+ border: 1px solid #ccc;
+ margin-top: 10px;
+ box-shadow: 0 -1px 0 #e5e5e5,0 0 2px rgba(0,0,0,.12),0 2px 4px rgba(0,0,0,.24);
+}
+
+.card-body {
+ padding: 15px;
+ width: 10000px;
+}
+
+.card-body, .card-right, .card-left {
+ display: table-cell;
+ vertical-align: top;
+}
+
+.card-left, .card>.pull-left {
+ padding: 15px;
+ padding-right: 0px;
+}
+.card-right, .card>.pull-right {
+ padding: 15px;
+ padding-left: 0px;
+}
+
+.card-list {
+ margin-top: 10px;
+}
+
+.card-list > .card:first-child {
+ border-top: 1px solid #ccc;
+}
+
+.card-list > .card {
+ margin-top: 0;
+ border-top: none;
+}
+
+/* ui */
+
+entity-list .btn-filter {
+ visibility: hidden;
+}
+
+entity-list:hover .btn-filter {
+ visibility: visible;
+}
+
+/* doc */
+
+.nitdoc .synopsys {
+ font-size: 2em;
+}
+
+.signature {
+ color: #666;
+ font-family: monospace;
+}
+
+.signature .name {
+ font-weight: bold;
+}
+
+.page-header .signature .name, .signature .signature .name {
+ font-weight: normal;
+}
+
+.signature .signature a {
+ color: #666;
+ font-family: monospace;
+}
+
+/* tabs */
+
+.nav-tabs li { cursor: pointer; }
+
+.nav>li.warning>a {
+ color: #fff;
+ background-color: #f0ad4e;
+}
+
+.nav>li.warning>a:focus, .nav>li.warning>a:hover {
+ background-color: #ff9c0f;
+}
+
+/* forms */
+
+.has-icon {
+ position: relative;
+}
+
+.has-icon .form-control {
+ padding-left: 35px;
+}
+
+.form-control-icon {
+ position: absolute;
+ top: 0;
+ left: 0;
+ z-index: 2;
+ display: block;
+ width: 34px;
+ height: 34px;
+ line-height: 34px;
+ text-align: center;
+ pointer-events: none;
+}
+
+/*
+ * Code Highlighting
+ */
+
+.nitcode a { color: inherit; text-decoration: inherit; } /* hide links */
+.nitcode a:hover { text-decoration: underline; } /* underline links */
+.nitcode span[title]:hover { text-decoration: underline; } /* underline titles */
+/* lexical raw tokens. independent of usage or semantic: */
+.nitcode .nc_c { color: gray; font-style: italic; } /* comment */
+.nitcode .nc_d { color: #3D8127; font-style: italic; } /* documentation comments */
+.nitcode .nc_k { font-weight: bold; } /* keyword */
+.nitcode .nc_o {} /* operator */
+.nitcode .nc_i {} /* standard identifier */
+.nitcode .nc_t { color: #445588; font-weight: bold; } /* type/class identifier */
+.nitcode .nc_a { color: #445588; font-style: italic; } /* old style attribute identifier */
+.nitcode .nc_l { color: #009999; } /* char and number literal */
+.nitcode .nc_s { color: #8F1546; } /* string literal */
+/* syntactic token usage. added because of their position in the AST */
+.nitcode .nc_ast { color: blue; } /* assert label */
+.nitcode .nc_la { color: blue; } /* break/continue label */
+.nitcode .nc_m { color: #445588; } /* module name */
+/* syntactic groups */
+.nitcode .nc_def { font-weight: bold; color: blue; } /* name used in a definition */
+.nitcode .nc_def.nc_a { color: blue; } /* name used in a attribute definition */
+.nitcode .nc_def.nc_t { color: blue; } /* name used in a class or vt definition */
+.nitcode .nc_ss { color: #9E6BEB; } /* superstrings */
+.nitcode .nc_cdef {} /* A whole class definition */
+.nitcode .nc_pdef {} /* A whole property definition */
+/* semantic token usage */
+.nitcode .nc_v { font-style: italic; } /* local variable or parameter */
+.nitcode .nc_vt { font-style: italic; } /* virtual type or formal type */
+.nitcode .nc_error { border: 1px red solid;} /* not used */
--- /dev/null
+/*! normalize.css v3.0.0 | MIT License | git.io/normalize */\r
+html {\r
+ font-family: sans-serif;\r
+ -ms-text-size-adjust: 100%;\r
+ -webkit-text-size-adjust: 100%;\r
+}\r
+body {\r
+ margin: 0;\r
+}\r
+article,\r
+aside,\r
+details,\r
+figcaption,\r
+figure,\r
+footer,\r
+header,\r
+hgroup,\r
+main,\r
+nav,\r
+section,\r
+summary {\r
+ display: block;\r
+}\r
+audio,\r
+canvas,\r
+progress,\r
+video {\r
+ display: inline-block;\r
+ vertical-align: baseline;\r
+}\r
+audio:not([controls]) {\r
+ display: none;\r
+ height: 0;\r
+}\r
+[hidden],\r
+template {\r
+ display: none;\r
+}\r
+a {\r
+ background: transparent;\r
+}\r
+a:active,\r
+a:hover {\r
+ outline: 0;\r
+}\r
+abbr[title] {\r
+ border-bottom: 1px dotted;\r
+}\r
+b,\r
+strong {\r
+ font-weight: bold;\r
+}\r
+dfn {\r
+ font-style: italic;\r
+}\r
+h1 {\r
+ font-size: 2em;\r
+ margin: 0.67em 0;\r
+}\r
+mark {\r
+ background: #ff0;\r
+ color: #000;\r
+}\r
+small {\r
+ font-size: 80%;\r
+}\r
+sub,\r
+sup {\r
+ font-size: 75%;\r
+ line-height: 0;\r
+ position: relative;\r
+ vertical-align: baseline;\r
+}\r
+sup {\r
+ top: -0.5em;\r
+}\r
+sub {\r
+ bottom: -0.25em;\r
+}\r
+img {\r
+ border: 0;\r
+}\r
+svg:not(:root) {\r
+ overflow: hidden;\r
+}\r
+figure {\r
+ margin: 1em 40px;\r
+}\r
+hr {\r
+ -moz-box-sizing: content-box;\r
+ box-sizing: content-box;\r
+ height: 0;\r
+}\r
+pre {\r
+ overflow: auto;\r
+}\r
+code,\r
+kbd,\r
+pre,\r
+samp {\r
+ font-family: monospace, monospace;\r
+ font-size: 1em;\r
+}\r
+button,\r
+input,\r
+optgroup,\r
+select,\r
+textarea {\r
+ color: inherit;\r
+ font: inherit;\r
+ margin: 0;\r
+}\r
+button {\r
+ overflow: visible;\r
+}\r
+button,\r
+select {\r
+ text-transform: none;\r
+}\r
+button,\r
+html input[type="button"],\r
+input[type="reset"],\r
+input[type="submit"] {\r
+ -webkit-appearance: button;\r
+ cursor: pointer;\r
+}\r
+button[disabled],\r
+html input[disabled] {\r
+ cursor: default;\r
+}\r
+button::-moz-focus-inner,\r
+input::-moz-focus-inner {\r
+ border: 0;\r
+ padding: 0;\r
+}\r
+input {\r
+ line-height: normal;\r
+}\r
+input[type="checkbox"],\r
+input[type="radio"] {\r
+ box-sizing: border-box;\r
+ padding: 0;\r
+}\r
+input[type="number"]::-webkit-inner-spin-button,\r
+input[type="number"]::-webkit-outer-spin-button {\r
+ height: auto;\r
+}\r
+input[type="search"] {\r
+ -webkit-appearance: textfield;\r
+ -moz-box-sizing: content-box;\r
+ -webkit-box-sizing: content-box;\r
+ box-sizing: content-box;\r
+}\r
+input[type="search"]::-webkit-search-cancel-button,\r
+input[type="search"]::-webkit-search-decoration {\r
+ -webkit-appearance: none;\r
+}\r
+fieldset {\r
+ border: 1px solid #c0c0c0;\r
+ margin: 0 2px;\r
+ padding: 0.35em 0.625em 0.75em;\r
+}\r
+legend {\r
+ border: 0;\r
+ padding: 0;\r
+}\r
+textarea {\r
+ overflow: auto;\r
+}\r
+optgroup {\r
+ font-weight: bold;\r
+}\r
+table {\r
+ border-collapse: collapse;\r
+ border-spacing: 0;\r
+}\r
+td,\r
+th {\r
+ padding: 0;\r
+}\r
+@media print {\r
+ * {\r
+ text-shadow: none !important;\r
+ color: #000 !important;\r
+ background: transparent !important;\r
+ box-shadow: none !important;\r
+ }\r
+ a,\r
+ a:visited {\r
+ text-decoration: underline;\r
+ }\r
+ a[href]:after {\r
+ content: " (" attr(href) ")";\r
+ }\r
+ abbr[title]:after {\r
+ content: " (" attr(title) ")";\r
+ }\r
+ a[href^="javascript:"]:after,\r
+ a[href^="#"]:after {\r
+ content: "";\r
+ }\r
+ pre,\r
+ blockquote {\r
+ border: 1px solid #999;\r
+ page-break-inside: avoid;\r
+ }\r
+ thead {\r
+ display: table-header-group;\r
+ }\r
+ tr,\r
+ img {\r
+ page-break-inside: avoid;\r
+ }\r
+ img {\r
+ max-width: 100% !important;\r
+ }\r
+ p,\r
+ h2,\r
+ h3 {\r
+ orphans: 3;\r
+ widows: 3;\r
+ }\r
+ h2,\r
+ h3 {\r
+ page-break-after: avoid;\r
+ }\r
+ select {\r
+ background: #fff !important;\r
+ }\r
+ .navbar {\r
+ display: none;\r
+ }\r
+ .table td,\r
+ .table th {\r
+ background-color: #fff !important;\r
+ }\r
+ .btn > .caret,\r
+ .dropup > .btn > .caret {\r
+ border-top-color: #000 !important;\r
+ }\r
+ .label {\r
+ border: 1px solid #000;\r
+ }\r
+ .table {\r
+ border-collapse: collapse !important;\r
+ }\r
+ .table-bordered th,\r
+ .table-bordered td {\r
+ border: 1px solid #ddd !important;\r
+ }\r
+}\r
+* {\r
+ -webkit-box-sizing: border-box;\r
+ -moz-box-sizing: border-box;\r
+ box-sizing: border-box;\r
+}\r
+*:before,\r
+*:after {\r
+ -webkit-box-sizing: border-box;\r
+ -moz-box-sizing: border-box;\r
+ box-sizing: border-box;\r
+}\r
+html {\r
+ font-size: 62.5%;\r
+ -webkit-tap-highlight-color: rgba(0, 0, 0, 0);\r
+}\r
+body {\r
+ font-family: sans-serif;\r
+ font-size: 14px;\r
+ line-height: 1.428571429;\r
+ color: #333333;\r
+ background-color: #f2f2f2;\r
+}\r
+input,\r
+button,\r
+select,\r
+textarea {\r
+ font-family: inherit;\r
+ font-size: inherit;\r
+ line-height: inherit;\r
+}\r
+a {\r
+ color: #0d8921;\r
+ text-decoration: none;\r
+}\r
+a:hover,\r
+a:focus {\r
+ color: #064310;\r
+ text-decoration: underline;\r
+}\r
+a:focus {\r
+ outline: thin dotted;\r
+ outline: 5px auto -webkit-focus-ring-color;\r
+ outline-offset: -2px;\r
+}\r
+figure {\r
+ margin: 0;\r
+}\r
+img {\r
+ vertical-align: middle;\r
+}\r
+.img-responsive,\r
+.thumbnail > img,\r
+.thumbnail a > img,\r
+.carousel-inner > .item > img,\r
+.carousel-inner > .item > a > img {\r
+ display: block;\r
+ max-width: 100%;\r
+ height: auto;\r
+}\r
+.img-rounded {\r
+ border-radius: 0px;\r
+}\r
+.img-thumbnail {\r
+ padding: 4px;\r
+ line-height: 1.428571429;\r
+ background-color: #f2f2f2;\r
+ border: 1px solid #dddddd;\r
+ border-radius: 0px;\r
+ -webkit-transition: all 0.2s ease-in-out;\r
+ transition: all 0.2s ease-in-out;\r
+ display: inline-block;\r
+ max-width: 100%;\r
+ height: auto;\r
+}\r
+.img-circle {\r
+ border-radius: 50%;\r
+}\r
+hr {\r
+ margin-top: 20px;\r
+ margin-bottom: 20px;\r
+ border: 0;\r
+ border-top: 1px solid #eeeeee;\r
+}\r
+.sr-only {\r
+ position: absolute;\r
+ width: 1px;\r
+ height: 1px;\r
+ margin: -1px;\r
+ padding: 0;\r
+ overflow: hidden;\r
+ clip: rect(0, 0, 0, 0);\r
+ border: 0;\r
+}\r
+h1,\r
+h2,\r
+h3,\r
+h4,\r
+h5,\r
+h6,\r
+.h1,\r
+.h2,\r
+.h3,\r
+.h4,\r
+.h5,\r
+.h6 {\r
+ font-family: sans-serif;\r
+ font-weight: 500;\r
+ line-height: 1.1;\r
+ color: inherit;\r
+}\r
+h1 small,\r
+h2 small,\r
+h3 small,\r
+h4 small,\r
+h5 small,\r
+h6 small,\r
+.h1 small,\r
+.h2 small,\r
+.h3 small,\r
+.h4 small,\r
+.h5 small,\r
+.h6 small,\r
+h1 .small,\r
+h2 .small,\r
+h3 .small,\r
+h4 .small,\r
+h5 .small,\r
+h6 .small,\r
+.h1 .small,\r
+.h2 .small,\r
+.h3 .small,\r
+.h4 .small,\r
+.h5 .small,\r
+.h6 .small {\r
+ font-weight: normal;\r
+ line-height: 1;\r
+ color: #999999;\r
+}\r
+h1,\r
+.h1,\r
+h2,\r
+.h2,\r
+h3,\r
+.h3 {\r
+ margin-top: 20px;\r
+ margin-bottom: 10px;\r
+}\r
+h1 small,\r
+.h1 small,\r
+h2 small,\r
+.h2 small,\r
+h3 small,\r
+.h3 small,\r
+h1 .small,\r
+.h1 .small,\r
+h2 .small,\r
+.h2 .small,\r
+h3 .small,\r
+.h3 .small {\r
+ font-size: 65%;\r
+}\r
+h4,\r
+.h4,\r
+h5,\r
+.h5,\r
+h6,\r
+.h6 {\r
+ margin-top: 10px;\r
+ margin-bottom: 10px;\r
+}\r
+h4 small,\r
+.h4 small,\r
+h5 small,\r
+.h5 small,\r
+h6 small,\r
+.h6 small,\r
+h4 .small,\r
+.h4 .small,\r
+h5 .small,\r
+.h5 .small,\r
+h6 .small,\r
+.h6 .small {\r
+ font-size: 75%;\r
+}\r
+h1,\r
+.h1 {\r
+ font-size: 36px;\r
+}\r
+h2,\r
+.h2 {\r
+ font-size: 30px;\r
+}\r
+h3,\r
+.h3 {\r
+ font-size: 23px;\r
+}\r
+h4,\r
+.h4 {\r
+ font-size: 17px;\r
+}\r
+h5,\r
+.h5 {\r
+ font-size: 14px;\r
+}\r
+h6,\r
+.h6 {\r
+ font-size: 11px;\r
+}\r
+p {\r
+ margin: 0 0 10px;\r
+}\r
+.lead {\r
+ margin-bottom: 20px;\r
+ font-size: 16px;\r
+ font-weight: 200;\r
+ line-height: 1.4;\r
+}\r
+@media (min-width: 768px) {\r
+ .lead {\r
+ font-size: 21px;\r
+ }\r
+}\r
+small,\r
+.small {\r
+ font-size: 85%;\r
+}\r
+cite {\r
+ font-style: normal;\r
+}\r
+.text-left {\r
+ text-align: left;\r
+}\r
+.text-right {\r
+ text-align: right;\r
+}\r
+.text-center {\r
+ text-align: center;\r
+}\r
+.text-justify {\r
+ text-align: justify;\r
+}\r
+.text-muted {\r
+ color: #999999;\r
+}\r
+.text-primary {\r
+ color: #0d8921;\r
+}\r
+a.text-primary:hover {\r
+ color: #095a16;\r
+}\r
+.text-success {\r
+ color: #5cb85c;\r
+}\r
+a.text-success:hover {\r
+ color: #449d44;\r
+}\r
+.text-info {\r
+ color: #5bc0de;\r
+}\r
+a.text-info:hover {\r
+ color: #31b0d5;\r
+}\r
+.text-warning {\r
+ color: #f0ad4e;\r
+}\r
+a.text-warning:hover {\r
+ color: #ec971f;\r
+}\r
+.text-danger {\r
+ color: #d9534f;\r
+}\r
+a.text-danger:hover {\r
+ color: #c9302c;\r
+}\r
+.bg-primary {\r
+ color: #fff;\r
+ background-color: #0d8921;\r
+}\r
+a.bg-primary:hover {\r
+ background-color: #095a16;\r
+}\r
+.bg-success {\r
+ background-color: #dff0d8;\r
+}\r
+a.bg-success:hover {\r
+ background-color: #c1e2b3;\r
+}\r
+.bg-info {\r
+ background-color: #d9edf7;\r
+}\r
+a.bg-info:hover {\r
+ background-color: #afd9ee;\r
+}\r
+.bg-warning {\r
+ background-color: #fcf8e3;\r
+}\r
+a.bg-warning:hover {\r
+ background-color: #f7ecb5;\r
+}\r
+.bg-danger {\r
+ background-color: #f2dede;\r
+}\r
+a.bg-danger:hover {\r
+ background-color: #e4b9b9;\r
+}\r
+.page-header {\r
+ padding-bottom: 9px;\r
+ margin: 40px 0 20px;\r
+ border-bottom: 1px solid #eeeeee;\r
+}\r
+ul,\r
+ol {\r
+ margin-top: 0;\r
+ margin-bottom: 10px;\r
+}\r
+ul ul,\r
+ol ul,\r
+ul ol,\r
+ol ol {\r
+ margin-bottom: 0;\r
+}\r
+.list-unstyled {\r
+ padding-left: 0;\r
+ list-style: none;\r
+}\r
+.list-inline {\r
+ padding-left: 0;\r
+ list-style: none;\r
+}\r
+.list-inline > li {\r
+ display: inline-block;\r
+ padding-left: 5px;\r
+ padding-right: 5px;\r
+}\r
+.list-inline > li:first-child {\r
+ padding-left: 0;\r
+}\r
+dl {\r
+ margin-top: 0;\r
+ margin-bottom: 20px;\r
+}\r
+dt,\r
+dd {\r
+ line-height: 1.428571429;\r
+}\r
+dt {\r
+ font-weight: bold;\r
+}\r
+dd {\r
+ margin-left: 0;\r
+}\r
+@media (min-width: 768px) {\r
+ .dl-horizontal dt {\r
+ float: left;\r
+ width: 160px;\r
+ clear: left;\r
+ text-align: right;\r
+ overflow: hidden;\r
+ text-overflow: ellipsis;\r
+ white-space: nowrap;\r
+ }\r
+ .dl-horizontal dd {\r
+ margin-left: 180px;\r
+ }\r
+}\r
+abbr[title],\r
+abbr[data-original-title] {\r
+ cursor: help;\r
+ border-bottom: 1px dotted #999999;\r
+}\r
+.initialism {\r
+ font-size: 90%;\r
+ text-transform: uppercase;\r
+}\r
+blockquote {\r
+ padding: 10px 20px;\r
+ margin: 0 0 20px;\r
+ font-size: 17.5px;\r
+ border-left: 5px solid #eeeeee;\r
+}\r
+blockquote p:last-child,\r
+blockquote ul:last-child,\r
+blockquote ol:last-child {\r
+ margin-bottom: 0;\r
+}\r
+blockquote footer,\r
+blockquote small,\r
+blockquote .small {\r
+ display: block;\r
+ font-size: 80%;\r
+ line-height: 1.428571429;\r
+ color: #999999;\r
+}\r
+blockquote footer:before,\r
+blockquote small:before,\r
+blockquote .small:before {\r
+ content: '\2014 \00A0';\r
+}\r
+.blockquote-reverse,\r
+blockquote.pull-right {\r
+ padding-right: 15px;\r
+ padding-left: 0;\r
+ border-right: 5px solid #eeeeee;\r
+ border-left: 0;\r
+ text-align: right;\r
+}\r
+.blockquote-reverse footer:before,\r
+blockquote.pull-right footer:before,\r
+.blockquote-reverse small:before,\r
+blockquote.pull-right small:before,\r
+.blockquote-reverse .small:before,\r
+blockquote.pull-right .small:before {\r
+ content: '';\r
+}\r
+.blockquote-reverse footer:after,\r
+blockquote.pull-right footer:after,\r
+.blockquote-reverse small:after,\r
+blockquote.pull-right small:after,\r
+.blockquote-reverse .small:after,\r
+blockquote.pull-right .small:after {\r
+ content: '\00A0 \2014';\r
+}\r
+blockquote:before,\r
+blockquote:after {\r
+ content: "";\r
+}\r
+address {\r
+ margin-bottom: 20px;\r
+ font-style: normal;\r
+ line-height: 1.428571429;\r
+}\r
+code,\r
+kbd,\r
+pre,\r
+samp {\r
+ font-family: monospace;\r
+}\r
+code {\r
+ padding: 2px 4px;\r
+ font-size: 90%;\r
+ color: #c7254e;\r
+ background-color: #f9f2f4;\r
+ white-space: nowrap;\r
+ border-radius: 0px;\r
+}\r
+kbd {\r
+ padding: 2px 4px;\r
+ font-size: 90%;\r
+ color: #ffffff;\r
+ background-color: #333333;\r
+ border-radius: 0px;\r
+ box-shadow: inset 0 -1px 0 rgba(0, 0, 0, 0.25);\r
+}\r
+pre {\r
+ display: block;\r
+ padding: 9.5px;\r
+ margin: 0 0 10px;\r
+ font-size: 13px;\r
+ line-height: 1.428571429;\r
+ word-break: break-all;\r
+ word-wrap: break-word;\r
+ color: #333333;\r
+ background-color: #f5f5f5;\r
+ border: 1px solid #cccccc;\r
+ border-radius: 0px;\r
+}\r
+pre code {\r
+ padding: 0;\r
+ font-size: inherit;\r
+ color: inherit;\r
+ white-space: pre-wrap;\r
+ background-color: transparent;\r
+ border-radius: 0;\r
+}\r
+.pre-scrollable {\r
+ max-height: 340px;\r
+ overflow-y: scroll;\r
+}\r
+.container {\r
+ margin-right: auto;\r
+ margin-left: auto;\r
+ padding-left: 15px;\r
+ padding-right: 15px;\r
+}\r
+@media (min-width: 768px) {\r
+ .container {\r
+ width: 750px;\r
+ }\r
+}\r
+@media (min-width: 992px) {\r
+ .container {\r
+ width: 970px;\r
+ }\r
+}\r
+@media (min-width: 1200px) {\r
+ .container {\r
+ width: 1170px;\r
+ }\r
+}\r
+.container-fluid {\r
+ margin-right: auto;\r
+ margin-left: auto;\r
+ padding-left: 15px;\r
+ padding-right: 15px;\r
+}\r
+.row {\r
+ margin-left: -15px;\r
+ margin-right: -15px;\r
+}\r
+.col-xs-1, .col-sm-1, .col-md-1, .col-lg-1, .col-xs-2, .col-sm-2, .col-md-2, .col-lg-2, .col-xs-3, .col-sm-3, .col-md-3, .col-lg-3, .col-xs-4, .col-sm-4, .col-md-4, .col-lg-4, .col-xs-5, .col-sm-5, .col-md-5, .col-lg-5, .col-xs-6, .col-sm-6, .col-md-6, .col-lg-6, .col-xs-7, .col-sm-7, .col-md-7, .col-lg-7, .col-xs-8, .col-sm-8, .col-md-8, .col-lg-8, .col-xs-9, .col-sm-9, .col-md-9, .col-lg-9, .col-xs-10, .col-sm-10, .col-md-10, .col-lg-10, .col-xs-11, .col-sm-11, .col-md-11, .col-lg-11, .col-xs-12, .col-sm-12, .col-md-12, .col-lg-12 {\r
+ position: relative;\r
+ min-height: 1px;\r
+ padding-left: 15px;\r
+ padding-right: 15px;\r
+}\r
+.col-xs-1, .col-xs-2, .col-xs-3, .col-xs-4, .col-xs-5, .col-xs-6, .col-xs-7, .col-xs-8, .col-xs-9, .col-xs-10, .col-xs-11, .col-xs-12 {\r
+ float: left;\r
+}\r
+.col-xs-12 {\r
+ width: 100%;\r
+}\r
+.col-xs-11 {\r
+ width: 91.66666666666666%;\r
+}\r
+.col-xs-10 {\r
+ width: 83.33333333333334%;\r
+}\r
+.col-xs-9 {\r
+ width: 75%;\r
+}\r
+.col-xs-8 {\r
+ width: 66.66666666666666%;\r
+}\r
+.col-xs-7 {\r
+ width: 58.333333333333336%;\r
+}\r
+.col-xs-6 {\r
+ width: 50%;\r
+}\r
+.col-xs-5 {\r
+ width: 41.66666666666667%;\r
+}\r
+.col-xs-4 {\r
+ width: 33.33333333333333%;\r
+}\r
+.col-xs-3 {\r
+ width: 25%;\r
+}\r
+.col-xs-2 {\r
+ width: 16.666666666666664%;\r
+}\r
+.col-xs-1 {\r
+ width: 8.333333333333332%;\r
+}\r
+.col-xs-pull-12 {\r
+ right: 100%;\r
+}\r
+.col-xs-pull-11 {\r
+ right: 91.66666666666666%;\r
+}\r
+.col-xs-pull-10 {\r
+ right: 83.33333333333334%;\r
+}\r
+.col-xs-pull-9 {\r
+ right: 75%;\r
+}\r
+.col-xs-pull-8 {\r
+ right: 66.66666666666666%;\r
+}\r
+.col-xs-pull-7 {\r
+ right: 58.333333333333336%;\r
+}\r
+.col-xs-pull-6 {\r
+ right: 50%;\r
+}\r
+.col-xs-pull-5 {\r
+ right: 41.66666666666667%;\r
+}\r
+.col-xs-pull-4 {\r
+ right: 33.33333333333333%;\r
+}\r
+.col-xs-pull-3 {\r
+ right: 25%;\r
+}\r
+.col-xs-pull-2 {\r
+ right: 16.666666666666664%;\r
+}\r
+.col-xs-pull-1 {\r
+ right: 8.333333333333332%;\r
+}\r
+.col-xs-pull-0 {\r
+ right: 0%;\r
+}\r
+.col-xs-push-12 {\r
+ left: 100%;\r
+}\r
+.col-xs-push-11 {\r
+ left: 91.66666666666666%;\r
+}\r
+.col-xs-push-10 {\r
+ left: 83.33333333333334%;\r
+}\r
+.col-xs-push-9 {\r
+ left: 75%;\r
+}\r
+.col-xs-push-8 {\r
+ left: 66.66666666666666%;\r
+}\r
+.col-xs-push-7 {\r
+ left: 58.333333333333336%;\r
+}\r
+.col-xs-push-6 {\r
+ left: 50%;\r
+}\r
+.col-xs-push-5 {\r
+ left: 41.66666666666667%;\r
+}\r
+.col-xs-push-4 {\r
+ left: 33.33333333333333%;\r
+}\r
+.col-xs-push-3 {\r
+ left: 25%;\r
+}\r
+.col-xs-push-2 {\r
+ left: 16.666666666666664%;\r
+}\r
+.col-xs-push-1 {\r
+ left: 8.333333333333332%;\r
+}\r
+.col-xs-push-0 {\r
+ left: 0%;\r
+}\r
+.col-xs-offset-12 {\r
+ margin-left: 100%;\r
+}\r
+.col-xs-offset-11 {\r
+ margin-left: 91.66666666666666%;\r
+}\r
+.col-xs-offset-10 {\r
+ margin-left: 83.33333333333334%;\r
+}\r
+.col-xs-offset-9 {\r
+ margin-left: 75%;\r
+}\r
+.col-xs-offset-8 {\r
+ margin-left: 66.66666666666666%;\r
+}\r
+.col-xs-offset-7 {\r
+ margin-left: 58.333333333333336%;\r
+}\r
+.col-xs-offset-6 {\r
+ margin-left: 50%;\r
+}\r
+.col-xs-offset-5 {\r
+ margin-left: 41.66666666666667%;\r
+}\r
+.col-xs-offset-4 {\r
+ margin-left: 33.33333333333333%;\r
+}\r
+.col-xs-offset-3 {\r
+ margin-left: 25%;\r
+}\r
+.col-xs-offset-2 {\r
+ margin-left: 16.666666666666664%;\r
+}\r
+.col-xs-offset-1 {\r
+ margin-left: 8.333333333333332%;\r
+}\r
+.col-xs-offset-0 {\r
+ margin-left: 0%;\r
+}\r
+@media (min-width: 768px) {\r
+ .col-sm-1, .col-sm-2, .col-sm-3, .col-sm-4, .col-sm-5, .col-sm-6, .col-sm-7, .col-sm-8, .col-sm-9, .col-sm-10, .col-sm-11, .col-sm-12 {\r
+ float: left;\r
+ }\r
+ .col-sm-12 {\r
+ width: 100%;\r
+ }\r
+ .col-sm-11 {\r
+ width: 91.66666666666666%;\r
+ }\r
+ .col-sm-10 {\r
+ width: 83.33333333333334%;\r
+ }\r
+ .col-sm-9 {\r
+ width: 75%;\r
+ }\r
+ .col-sm-8 {\r
+ width: 66.66666666666666%;\r
+ }\r
+ .col-sm-7 {\r
+ width: 58.333333333333336%;\r
+ }\r
+ .col-sm-6 {\r
+ width: 50%;\r
+ }\r
+ .col-sm-5 {\r
+ width: 41.66666666666667%;\r
+ }\r
+ .col-sm-4 {\r
+ width: 33.33333333333333%;\r
+ }\r
+ .col-sm-3 {\r
+ width: 25%;\r
+ }\r
+ .col-sm-2 {\r
+ width: 16.666666666666664%;\r
+ }\r
+ .col-sm-1 {\r
+ width: 8.333333333333332%;\r
+ }\r
+ .col-sm-pull-12 {\r
+ right: 100%;\r
+ }\r
+ .col-sm-pull-11 {\r
+ right: 91.66666666666666%;\r
+ }\r
+ .col-sm-pull-10 {\r
+ right: 83.33333333333334%;\r
+ }\r
+ .col-sm-pull-9 {\r
+ right: 75%;\r
+ }\r
+ .col-sm-pull-8 {\r
+ right: 66.66666666666666%;\r
+ }\r
+ .col-sm-pull-7 {\r
+ right: 58.333333333333336%;\r
+ }\r
+ .col-sm-pull-6 {\r
+ right: 50%;\r
+ }\r
+ .col-sm-pull-5 {\r
+ right: 41.66666666666667%;\r
+ }\r
+ .col-sm-pull-4 {\r
+ right: 33.33333333333333%;\r
+ }\r
+ .col-sm-pull-3 {\r
+ right: 25%;\r
+ }\r
+ .col-sm-pull-2 {\r
+ right: 16.666666666666664%;\r
+ }\r
+ .col-sm-pull-1 {\r
+ right: 8.333333333333332%;\r
+ }\r
+ .col-sm-pull-0 {\r
+ right: 0%;\r
+ }\r
+ .col-sm-push-12 {\r
+ left: 100%;\r
+ }\r
+ .col-sm-push-11 {\r
+ left: 91.66666666666666%;\r
+ }\r
+ .col-sm-push-10 {\r
+ left: 83.33333333333334%;\r
+ }\r
+ .col-sm-push-9 {\r
+ left: 75%;\r
+ }\r
+ .col-sm-push-8 {\r
+ left: 66.66666666666666%;\r
+ }\r
+ .col-sm-push-7 {\r
+ left: 58.333333333333336%;\r
+ }\r
+ .col-sm-push-6 {\r
+ left: 50%;\r
+ }\r
+ .col-sm-push-5 {\r
+ left: 41.66666666666667%;\r
+ }\r
+ .col-sm-push-4 {\r
+ left: 33.33333333333333%;\r
+ }\r
+ .col-sm-push-3 {\r
+ left: 25%;\r
+ }\r
+ .col-sm-push-2 {\r
+ left: 16.666666666666664%;\r
+ }\r
+ .col-sm-push-1 {\r
+ left: 8.333333333333332%;\r
+ }\r
+ .col-sm-push-0 {\r
+ left: 0%;\r
+ }\r
+ .col-sm-offset-12 {\r
+ margin-left: 100%;\r
+ }\r
+ .col-sm-offset-11 {\r
+ margin-left: 91.66666666666666%;\r
+ }\r
+ .col-sm-offset-10 {\r
+ margin-left: 83.33333333333334%;\r
+ }\r
+ .col-sm-offset-9 {\r
+ margin-left: 75%;\r
+ }\r
+ .col-sm-offset-8 {\r
+ margin-left: 66.66666666666666%;\r
+ }\r
+ .col-sm-offset-7 {\r
+ margin-left: 58.333333333333336%;\r
+ }\r
+ .col-sm-offset-6 {\r
+ margin-left: 50%;\r
+ }\r
+ .col-sm-offset-5 {\r
+ margin-left: 41.66666666666667%;\r
+ }\r
+ .col-sm-offset-4 {\r
+ margin-left: 33.33333333333333%;\r
+ }\r
+ .col-sm-offset-3 {\r
+ margin-left: 25%;\r
+ }\r
+ .col-sm-offset-2 {\r
+ margin-left: 16.666666666666664%;\r
+ }\r
+ .col-sm-offset-1 {\r
+ margin-left: 8.333333333333332%;\r
+ }\r
+ .col-sm-offset-0 {\r
+ margin-left: 0%;\r
+ }\r
+}\r
+@media (min-width: 992px) {\r
+ .col-md-1, .col-md-2, .col-md-3, .col-md-4, .col-md-5, .col-md-6, .col-md-7, .col-md-8, .col-md-9, .col-md-10, .col-md-11, .col-md-12 {\r
+ float: left;\r
+ }\r
+ .col-md-12 {\r
+ width: 100%;\r
+ }\r
+ .col-md-11 {\r
+ width: 91.66666666666666%;\r
+ }\r
+ .col-md-10 {\r
+ width: 83.33333333333334%;\r
+ }\r
+ .col-md-9 {\r
+ width: 75%;\r
+ }\r
+ .col-md-8 {\r
+ width: 66.66666666666666%;\r
+ }\r
+ .col-md-7 {\r
+ width: 58.333333333333336%;\r
+ }\r
+ .col-md-6 {\r
+ width: 50%;\r
+ }\r
+ .col-md-5 {\r
+ width: 41.66666666666667%;\r
+ }\r
+ .col-md-4 {\r
+ width: 33.33333333333333%;\r
+ }\r
+ .col-md-3 {\r
+ width: 25%;\r
+ }\r
+ .col-md-2 {\r
+ width: 16.666666666666664%;\r
+ }\r
+ .col-md-1 {\r
+ width: 8.333333333333332%;\r
+ }\r
+ .col-md-pull-12 {\r
+ right: 100%;\r
+ }\r
+ .col-md-pull-11 {\r
+ right: 91.66666666666666%;\r
+ }\r
+ .col-md-pull-10 {\r
+ right: 83.33333333333334%;\r
+ }\r
+ .col-md-pull-9 {\r
+ right: 75%;\r
+ }\r
+ .col-md-pull-8 {\r
+ right: 66.66666666666666%;\r
+ }\r
+ .col-md-pull-7 {\r
+ right: 58.333333333333336%;\r
+ }\r
+ .col-md-pull-6 {\r
+ right: 50%;\r
+ }\r
+ .col-md-pull-5 {\r
+ right: 41.66666666666667%;\r
+ }\r
+ .col-md-pull-4 {\r
+ right: 33.33333333333333%;\r
+ }\r
+ .col-md-pull-3 {\r
+ right: 25%;\r
+ }\r
+ .col-md-pull-2 {\r
+ right: 16.666666666666664%;\r
+ }\r
+ .col-md-pull-1 {\r
+ right: 8.333333333333332%;\r
+ }\r
+ .col-md-pull-0 {\r
+ right: 0%;\r
+ }\r
+ .col-md-push-12 {\r
+ left: 100%;\r
+ }\r
+ .col-md-push-11 {\r
+ left: 91.66666666666666%;\r
+ }\r
+ .col-md-push-10 {\r
+ left: 83.33333333333334%;\r
+ }\r
+ .col-md-push-9 {\r
+ left: 75%;\r
+ }\r
+ .col-md-push-8 {\r
+ left: 66.66666666666666%;\r
+ }\r
+ .col-md-push-7 {\r
+ left: 58.333333333333336%;\r
+ }\r
+ .col-md-push-6 {\r
+ left: 50%;\r
+ }\r
+ .col-md-push-5 {\r
+ left: 41.66666666666667%;\r
+ }\r
+ .col-md-push-4 {\r
+ left: 33.33333333333333%;\r
+ }\r
+ .col-md-push-3 {\r
+ left: 25%;\r
+ }\r
+ .col-md-push-2 {\r
+ left: 16.666666666666664%;\r
+ }\r
+ .col-md-push-1 {\r
+ left: 8.333333333333332%;\r
+ }\r
+ .col-md-push-0 {\r
+ left: 0%;\r
+ }\r
+ .col-md-offset-12 {\r
+ margin-left: 100%;\r
+ }\r
+ .col-md-offset-11 {\r
+ margin-left: 91.66666666666666%;\r
+ }\r
+ .col-md-offset-10 {\r
+ margin-left: 83.33333333333334%;\r
+ }\r
+ .col-md-offset-9 {\r
+ margin-left: 75%;\r
+ }\r
+ .col-md-offset-8 {\r
+ margin-left: 66.66666666666666%;\r
+ }\r
+ .col-md-offset-7 {\r
+ margin-left: 58.333333333333336%;\r
+ }\r
+ .col-md-offset-6 {\r
+ margin-left: 50%;\r
+ }\r
+ .col-md-offset-5 {\r
+ margin-left: 41.66666666666667%;\r
+ }\r
+ .col-md-offset-4 {\r
+ margin-left: 33.33333333333333%;\r
+ }\r
+ .col-md-offset-3 {\r
+ margin-left: 25%;\r
+ }\r
+ .col-md-offset-2 {\r
+ margin-left: 16.666666666666664%;\r
+ }\r
+ .col-md-offset-1 {\r
+ margin-left: 8.333333333333332%;\r
+ }\r
+ .col-md-offset-0 {\r
+ margin-left: 0%;\r
+ }\r
+}\r
+@media (min-width: 1200px) {\r
+ .col-lg-1, .col-lg-2, .col-lg-3, .col-lg-4, .col-lg-5, .col-lg-6, .col-lg-7, .col-lg-8, .col-lg-9, .col-lg-10, .col-lg-11, .col-lg-12 {\r
+ float: left;\r
+ }\r
+ .col-lg-12 {\r
+ width: 100%;\r
+ }\r
+ .col-lg-11 {\r
+ width: 91.66666666666666%;\r
+ }\r
+ .col-lg-10 {\r
+ width: 83.33333333333334%;\r
+ }\r
+ .col-lg-9 {\r
+ width: 75%;\r
+ }\r
+ .col-lg-8 {\r
+ width: 66.66666666666666%;\r
+ }\r
+ .col-lg-7 {\r
+ width: 58.333333333333336%;\r
+ }\r
+ .col-lg-6 {\r
+ width: 50%;\r
+ }\r
+ .col-lg-5 {\r
+ width: 41.66666666666667%;\r
+ }\r
+ .col-lg-4 {\r
+ width: 33.33333333333333%;\r
+ }\r
+ .col-lg-3 {\r
+ width: 25%;\r
+ }\r
+ .col-lg-2 {\r
+ width: 16.666666666666664%;\r
+ }\r
+ .col-lg-1 {\r
+ width: 8.333333333333332%;\r
+ }\r
+ .col-lg-pull-12 {\r
+ right: 100%;\r
+ }\r
+ .col-lg-pull-11 {\r
+ right: 91.66666666666666%;\r
+ }\r
+ .col-lg-pull-10 {\r
+ right: 83.33333333333334%;\r
+ }\r
+ .col-lg-pull-9 {\r
+ right: 75%;\r
+ }\r
+ .col-lg-pull-8 {\r
+ right: 66.66666666666666%;\r
+ }\r
+ .col-lg-pull-7 {\r
+ right: 58.333333333333336%;\r
+ }\r
+ .col-lg-pull-6 {\r
+ right: 50%;\r
+ }\r
+ .col-lg-pull-5 {\r
+ right: 41.66666666666667%;\r
+ }\r
+ .col-lg-pull-4 {\r
+ right: 33.33333333333333%;\r
+ }\r
+ .col-lg-pull-3 {\r
+ right: 25%;\r
+ }\r
+ .col-lg-pull-2 {\r
+ right: 16.666666666666664%;\r
+ }\r
+ .col-lg-pull-1 {\r
+ right: 8.333333333333332%;\r
+ }\r
+ .col-lg-pull-0 {\r
+ right: 0%;\r
+ }\r
+ .col-lg-push-12 {\r
+ left: 100%;\r
+ }\r
+ .col-lg-push-11 {\r
+ left: 91.66666666666666%;\r
+ }\r
+ .col-lg-push-10 {\r
+ left: 83.33333333333334%;\r
+ }\r
+ .col-lg-push-9 {\r
+ left: 75%;\r
+ }\r
+ .col-lg-push-8 {\r
+ left: 66.66666666666666%;\r
+ }\r
+ .col-lg-push-7 {\r
+ left: 58.333333333333336%;\r
+ }\r
+ .col-lg-push-6 {\r
+ left: 50%;\r
+ }\r
+ .col-lg-push-5 {\r
+ left: 41.66666666666667%;\r
+ }\r
+ .col-lg-push-4 {\r
+ left: 33.33333333333333%;\r
+ }\r
+ .col-lg-push-3 {\r
+ left: 25%;\r
+ }\r
+ .col-lg-push-2 {\r
+ left: 16.666666666666664%;\r
+ }\r
+ .col-lg-push-1 {\r
+ left: 8.333333333333332%;\r
+ }\r
+ .col-lg-push-0 {\r
+ left: 0%;\r
+ }\r
+ .col-lg-offset-12 {\r
+ margin-left: 100%;\r
+ }\r
+ .col-lg-offset-11 {\r
+ margin-left: 91.66666666666666%;\r
+ }\r
+ .col-lg-offset-10 {\r
+ margin-left: 83.33333333333334%;\r
+ }\r
+ .col-lg-offset-9 {\r
+ margin-left: 75%;\r
+ }\r
+ .col-lg-offset-8 {\r
+ margin-left: 66.66666666666666%;\r
+ }\r
+ .col-lg-offset-7 {\r
+ margin-left: 58.333333333333336%;\r
+ }\r
+ .col-lg-offset-6 {\r
+ margin-left: 50%;\r
+ }\r
+ .col-lg-offset-5 {\r
+ margin-left: 41.66666666666667%;\r
+ }\r
+ .col-lg-offset-4 {\r
+ margin-left: 33.33333333333333%;\r
+ }\r
+ .col-lg-offset-3 {\r
+ margin-left: 25%;\r
+ }\r
+ .col-lg-offset-2 {\r
+ margin-left: 16.666666666666664%;\r
+ }\r
+ .col-lg-offset-1 {\r
+ margin-left: 8.333333333333332%;\r
+ }\r
+ .col-lg-offset-0 {\r
+ margin-left: 0%;\r
+ }\r
+}\r
+table {\r
+ max-width: 100%;\r
+ background-color: transparent;\r
+}\r
+th {\r
+ text-align: left;\r
+}\r
+.table {\r
+ width: 100%;\r
+ margin-bottom: 20px;\r
+}\r
+.table > thead > tr > th,\r
+.table > tbody > tr > th,\r
+.table > tfoot > tr > th,\r
+.table > thead > tr > td,\r
+.table > tbody > tr > td,\r
+.table > tfoot > tr > td {\r
+ padding: 8px;\r
+ line-height: 1.428571429;\r
+ vertical-align: top;\r
+ border-top: 1px solid #dddddd;\r
+}\r
+.table > thead > tr > th {\r
+ vertical-align: bottom;\r
+ border-bottom: 2px solid #dddddd;\r
+}\r
+.table > caption + thead > tr:first-child > th,\r
+.table > colgroup + thead > tr:first-child > th,\r
+.table > thead:first-child > tr:first-child > th,\r
+.table > caption + thead > tr:first-child > td,\r
+.table > colgroup + thead > tr:first-child > td,\r
+.table > thead:first-child > tr:first-child > td {\r
+ border-top: 0;\r
+}\r
+.table > tbody + tbody {\r
+ border-top: 2px solid #dddddd;\r
+}\r
+.table .table {\r
+ background-color: #f2f2f2;\r
+}\r
+.table-condensed > thead > tr > th,\r
+.table-condensed > tbody > tr > th,\r
+.table-condensed > tfoot > tr > th,\r
+.table-condensed > thead > tr > td,\r
+.table-condensed > tbody > tr > td,\r
+.table-condensed > tfoot > tr > td {\r
+ padding: 5px;\r
+}\r
+.table-bordered {\r
+ border: 1px solid #dddddd;\r
+}\r
+.table-bordered > thead > tr > th,\r
+.table-bordered > tbody > tr > th,\r
+.table-bordered > tfoot > tr > th,\r
+.table-bordered > thead > tr > td,\r
+.table-bordered > tbody > tr > td,\r
+.table-bordered > tfoot > tr > td {\r
+ border: 1px solid #dddddd;\r
+}\r
+.table-bordered > thead > tr > th,\r
+.table-bordered > thead > tr > td {\r
+ border-bottom-width: 2px;\r
+}\r
+.table-striped > tbody > tr:nth-child(odd) > td,\r
+.table-striped > tbody > tr:nth-child(odd) > th {\r
+ background-color: #f9f9f9;\r
+}\r
+.table-hover > tbody > tr:hover > td,\r
+.table-hover > tbody > tr:hover > th {\r
+ background-color: #dbdbdb;\r
+}\r
+table col[class*="col-"] {\r
+ position: static;\r
+ float: none;\r
+ display: table-column;\r
+}\r
+table td[class*="col-"],\r
+table th[class*="col-"] {\r
+ position: static;\r
+ float: none;\r
+ display: table-cell;\r
+}\r
+.table > thead > tr > td.active,\r
+.table > tbody > tr > td.active,\r
+.table > tfoot > tr > td.active,\r
+.table > thead > tr > th.active,\r
+.table > tbody > tr > th.active,\r
+.table > tfoot > tr > th.active,\r
+.table > thead > tr.active > td,\r
+.table > tbody > tr.active > td,\r
+.table > tfoot > tr.active > td,\r
+.table > thead > tr.active > th,\r
+.table > tbody > tr.active > th,\r
+.table > tfoot > tr.active > th {\r
+ background-color: #dbdbdb;\r
+}\r
+.table-hover > tbody > tr > td.active:hover,\r
+.table-hover > tbody > tr > th.active:hover,\r
+.table-hover > tbody > tr.active:hover > td,\r
+.table-hover > tbody > tr.active:hover > th {\r
+ background-color: #cecece;\r
+}\r
+.table > thead > tr > td.success,\r
+.table > tbody > tr > td.success,\r
+.table > tfoot > tr > td.success,\r
+.table > thead > tr > th.success,\r
+.table > tbody > tr > th.success,\r
+.table > tfoot > tr > th.success,\r
+.table > thead > tr.success > td,\r
+.table > tbody > tr.success > td,\r
+.table > tfoot > tr.success > td,\r
+.table > thead > tr.success > th,\r
+.table > tbody > tr.success > th,\r
+.table > tfoot > tr.success > th {\r
+ background-color: #dff0d8;\r
+}\r
+.table-hover > tbody > tr > td.success:hover,\r
+.table-hover > tbody > tr > th.success:hover,\r
+.table-hover > tbody > tr.success:hover > td,\r
+.table-hover > tbody > tr.success:hover > th {\r
+ background-color: #d0e9c6;\r
+}\r
+.table > thead > tr > td.info,\r
+.table > tbody > tr > td.info,\r
+.table > tfoot > tr > td.info,\r
+.table > thead > tr > th.info,\r
+.table > tbody > tr > th.info,\r
+.table > tfoot > tr > th.info,\r
+.table > thead > tr.info > td,\r
+.table > tbody > tr.info > td,\r
+.table > tfoot > tr.info > td,\r
+.table > thead > tr.info > th,\r
+.table > tbody > tr.info > th,\r
+.table > tfoot > tr.info > th {\r
+ background-color: #d9edf7;\r
+}\r
+.table-hover > tbody > tr > td.info:hover,\r
+.table-hover > tbody > tr > th.info:hover,\r
+.table-hover > tbody > tr.info:hover > td,\r
+.table-hover > tbody > tr.info:hover > th {\r
+ background-color: #c4e3f3;\r
+}\r
+.table > thead > tr > td.warning,\r
+.table > tbody > tr > td.warning,\r
+.table > tfoot > tr > td.warning,\r
+.table > thead > tr > th.warning,\r
+.table > tbody > tr > th.warning,\r
+.table > tfoot > tr > th.warning,\r
+.table > thead > tr.warning > td,\r
+.table > tbody > tr.warning > td,\r
+.table > tfoot > tr.warning > td,\r
+.table > thead > tr.warning > th,\r
+.table > tbody > tr.warning > th,\r
+.table > tfoot > tr.warning > th {\r
+ background-color: #fcf8e3;\r
+}\r
+.table-hover > tbody > tr > td.warning:hover,\r
+.table-hover > tbody > tr > th.warning:hover,\r
+.table-hover > tbody > tr.warning:hover > td,\r
+.table-hover > tbody > tr.warning:hover > th {\r
+ background-color: #faf2cc;\r
+}\r
+.table > thead > tr > td.danger,\r
+.table > tbody > tr > td.danger,\r
+.table > tfoot > tr > td.danger,\r
+.table > thead > tr > th.danger,\r
+.table > tbody > tr > th.danger,\r
+.table > tfoot > tr > th.danger,\r
+.table > thead > tr.danger > td,\r
+.table > tbody > tr.danger > td,\r
+.table > tfoot > tr.danger > td,\r
+.table > thead > tr.danger > th,\r
+.table > tbody > tr.danger > th,\r
+.table > tfoot > tr.danger > th {\r
+ background-color: #f2dede;\r
+}\r
+.table-hover > tbody > tr > td.danger:hover,\r
+.table-hover > tbody > tr > th.danger:hover,\r
+.table-hover > tbody > tr.danger:hover > td,\r
+.table-hover > tbody > tr.danger:hover > th {\r
+ background-color: #ebcccc;\r
+}\r
+@media (max-width: 767px) {\r
+ .table-responsive {\r
+ width: 100%;\r
+ margin-bottom: 15px;\r
+ overflow-y: hidden;\r
+ overflow-x: scroll;\r
+ -ms-overflow-style: -ms-autohiding-scrollbar;\r
+ border: 1px solid #dddddd;\r
+ -webkit-overflow-scrolling: touch;\r
+ }\r
+ .table-responsive > .table {\r
+ margin-bottom: 0;\r
+ }\r
+ .table-responsive > .table > thead > tr > th,\r
+ .table-responsive > .table > tbody > tr > th,\r
+ .table-responsive > .table > tfoot > tr > th,\r
+ .table-responsive > .table > thead > tr > td,\r
+ .table-responsive > .table > tbody > tr > td,\r
+ .table-responsive > .table > tfoot > tr > td {\r
+ white-space: nowrap;\r
+ }\r
+ .table-responsive > .table-bordered {\r
+ border: 0;\r
+ }\r
+ .table-responsive > .table-bordered > thead > tr > th:first-child,\r
+ .table-responsive > .table-bordered > tbody > tr > th:first-child,\r
+ .table-responsive > .table-bordered > tfoot > tr > th:first-child,\r
+ .table-responsive > .table-bordered > thead > tr > td:first-child,\r
+ .table-responsive > .table-bordered > tbody > tr > td:first-child,\r
+ .table-responsive > .table-bordered > tfoot > tr > td:first-child {\r
+ border-left: 0;\r
+ }\r
+ .table-responsive > .table-bordered > thead > tr > th:last-child,\r
+ .table-responsive > .table-bordered > tbody > tr > th:last-child,\r
+ .table-responsive > .table-bordered > tfoot > tr > th:last-child,\r
+ .table-responsive > .table-bordered > thead > tr > td:last-child,\r
+ .table-responsive > .table-bordered > tbody > tr > td:last-child,\r
+ .table-responsive > .table-bordered > tfoot > tr > td:last-child {\r
+ border-right: 0;\r
+ }\r
+ .table-responsive > .table-bordered > tbody > tr:last-child > th,\r
+ .table-responsive > .table-bordered > tfoot > tr:last-child > th,\r
+ .table-responsive > .table-bordered > tbody > tr:last-child > td,\r
+ .table-responsive > .table-bordered > tfoot > tr:last-child > td {\r
+ border-bottom: 0;\r
+ }\r
+}\r
+fieldset {\r
+ padding: 0;\r
+ margin: 0;\r
+ border: 0;\r
+ min-width: 0;\r
+}\r
+legend {\r
+ display: block;\r
+ width: 100%;\r
+ padding: 0;\r
+ margin-bottom: 20px;\r
+ font-size: 21px;\r
+ line-height: inherit;\r
+ color: #333333;\r
+ border: 0;\r
+ border-bottom: 1px solid #e5e5e5;\r
+}\r
+label {\r
+ display: inline-block;\r
+ margin-bottom: 5px;\r
+ font-weight: bold;\r
+}\r
+input[type="search"] {\r
+ -webkit-box-sizing: border-box;\r
+ -moz-box-sizing: border-box;\r
+ box-sizing: border-box;\r
+}\r
+input[type="radio"],\r
+input[type="checkbox"] {\r
+ margin: 4px 0 0;\r
+ margin-top: 1px \9;\r
+ /* IE8-9 */\r
+\r
+ line-height: normal;\r
+}\r
+input[type="file"] {\r
+ display: block;\r
+}\r
+input[type="range"] {\r
+ display: block;\r
+ width: 100%;\r
+}\r
+select[multiple],\r
+select[size] {\r
+ height: auto;\r
+}\r
+input[type="file"]:focus,\r
+input[type="radio"]:focus,\r
+input[type="checkbox"]:focus {\r
+ outline: thin dotted;\r
+ outline: 5px auto -webkit-focus-ring-color;\r
+ outline-offset: -2px;\r
+}\r
+output {\r
+ display: block;\r
+ padding-top: 7px;\r
+ font-size: 14px;\r
+ line-height: 1.428571429;\r
+ color: #555555;\r
+}\r
+.form-control {\r
+ display: block;\r
+ width: 100%;\r
+ height: 34px;\r
+ padding: 6px 12px;\r
+ font-size: 14px;\r
+ line-height: 1.428571429;\r
+ color: #555555;\r
+ background-color: #ffffff;\r
+ background-image: none;\r
+ border: 1px solid #cccccc;\r
+ border-radius: 0px;\r
+ -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);\r
+ box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);\r
+ -webkit-transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s;\r
+ transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s;\r
+}\r
+.form-control:focus {\r
+ border-color: #66afe9;\r
+ outline: 0;\r
+ -webkit-box-shadow: inset 0 1px 1px rgba(0,0,0,.075), 0 0 8px rgba(102, 175, 233, 0.6);\r
+ box-shadow: inset 0 1px 1px rgba(0,0,0,.075), 0 0 8px rgba(102, 175, 233, 0.6);\r
+}\r
+.form-control::-moz-placeholder {\r
+ color: #999999;\r
+ opacity: 1;\r
+}\r
+.form-control:-ms-input-placeholder {\r
+ color: #999999;\r
+}\r
+.form-control::-webkit-input-placeholder {\r
+ color: #999999;\r
+}\r
+.form-control[disabled],\r
+.form-control[readonly],\r
+fieldset[disabled] .form-control {\r
+ cursor: not-allowed;\r
+ background-color: #eeeeee;\r
+ opacity: 1;\r
+}\r
+textarea.form-control {\r
+ height: auto;\r
+}\r
+input[type="search"] {\r
+ -webkit-appearance: none;\r
+}\r
+input[type="date"] {\r
+ line-height: 34px;\r
+}\r
+.form-group {\r
+ margin-bottom: 15px;\r
+}\r
+.radio,\r
+.checkbox {\r
+ display: block;\r
+ min-height: 20px;\r
+ margin-top: 10px;\r
+ margin-bottom: 10px;\r
+ padding-left: 20px;\r
+}\r
+.radio label,\r
+.checkbox label {\r
+ display: inline;\r
+ font-weight: normal;\r
+ cursor: pointer;\r
+}\r
+.radio input[type="radio"],\r
+.radio-inline input[type="radio"],\r
+.checkbox input[type="checkbox"],\r
+.checkbox-inline input[type="checkbox"] {\r
+ float: left;\r
+ margin-left: -20px;\r
+}\r
+.radio + .radio,\r
+.checkbox + .checkbox {\r
+ margin-top: -5px;\r
+}\r
+.radio-inline,\r
+.checkbox-inline {\r
+ display: inline-block;\r
+ padding-left: 20px;\r
+ margin-bottom: 0;\r
+ vertical-align: middle;\r
+ font-weight: normal;\r
+ cursor: pointer;\r
+}\r
+.radio-inline + .radio-inline,\r
+.checkbox-inline + .checkbox-inline {\r
+ margin-top: 0;\r
+ margin-left: 10px;\r
+}\r
+input[type="radio"][disabled],\r
+input[type="checkbox"][disabled],\r
+.radio[disabled],\r
+.radio-inline[disabled],\r
+.checkbox[disabled],\r
+.checkbox-inline[disabled],\r
+fieldset[disabled] input[type="radio"],\r
+fieldset[disabled] input[type="checkbox"],\r
+fieldset[disabled] .radio,\r
+fieldset[disabled] .radio-inline,\r
+fieldset[disabled] .checkbox,\r
+fieldset[disabled] .checkbox-inline {\r
+ cursor: not-allowed;\r
+}\r
+.input-sm {\r
+ height: 30px;\r
+ padding: 5px 10px;\r
+ font-size: 12px;\r
+ line-height: 1.5;\r
+ border-radius: 0px;\r
+}\r
+select.input-sm {\r
+ height: 30px;\r
+ line-height: 30px;\r
+}\r
+textarea.input-sm,\r
+select[multiple].input-sm {\r
+ height: auto;\r
+}\r
+.input-lg {\r
+ height: 45px;\r
+ padding: 10px 16px;\r
+ font-size: 18px;\r
+ line-height: 1.33;\r
+ border-radius: 0px;\r
+}\r
+select.input-lg {\r
+ height: 45px;\r
+ line-height: 45px;\r
+}\r
+textarea.input-lg,\r
+select[multiple].input-lg {\r
+ height: auto;\r
+}\r
+.has-feedback {\r
+ position: relative;\r
+}\r
+.has-feedback .form-control {\r
+ padding-right: 42.5px;\r
+}\r
+.has-feedback .form-control-feedback {\r
+ position: absolute;\r
+ top: 25px;\r
+ right: 0;\r
+ display: block;\r
+ width: 34px;\r
+ height: 34px;\r
+ line-height: 34px;\r
+ text-align: center;\r
+}\r
+.has-success .help-block,\r
+.has-success .control-label,\r
+.has-success .radio,\r
+.has-success .checkbox,\r
+.has-success .radio-inline,\r
+.has-success .checkbox-inline {\r
+ color: #5cb85c;\r
+}\r
+.has-success .form-control {\r
+ border-color: #5cb85c;\r
+ -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);\r
+ box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);\r
+}\r
+.has-success .form-control:focus {\r
+ border-color: #449d44;\r
+ -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075), 0 0 6px #a3d7a3;\r
+ box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075), 0 0 6px #a3d7a3;\r
+}\r
+.has-success .input-group-addon {\r
+ color: #5cb85c;\r
+ border-color: #5cb85c;\r
+ background-color: #dff0d8;\r
+}\r
+.has-success .form-control-feedback {\r
+ color: #5cb85c;\r
+}\r
+.has-warning .help-block,\r
+.has-warning .control-label,\r
+.has-warning .radio,\r
+.has-warning .checkbox,\r
+.has-warning .radio-inline,\r
+.has-warning .checkbox-inline {\r
+ color: #f0ad4e;\r
+}\r
+.has-warning .form-control {\r
+ border-color: #f0ad4e;\r
+ -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);\r
+ box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);\r
+}\r
+.has-warning .form-control:focus {\r
+ border-color: #ec971f;\r
+ -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075), 0 0 6px #f8d9ac;\r
+ box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075), 0 0 6px #f8d9ac;\r
+}\r
+.has-warning .input-group-addon {\r
+ color: #f0ad4e;\r
+ border-color: #f0ad4e;\r
+ background-color: #fcf8e3;\r
+}\r
+.has-warning .form-control-feedback {\r
+ color: #f0ad4e;\r
+}\r
+.has-error .help-block,\r
+.has-error .control-label,\r
+.has-error .radio,\r
+.has-error .checkbox,\r
+.has-error .radio-inline,\r
+.has-error .checkbox-inline {\r
+ color: #d9534f;\r
+}\r
+.has-error .form-control {\r
+ border-color: #d9534f;\r
+ -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);\r
+ box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);\r
+}\r
+.has-error .form-control:focus {\r
+ border-color: #c9302c;\r
+ -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075), 0 0 6px #eba5a3;\r
+ box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075), 0 0 6px #eba5a3;\r
+}\r
+.has-error .input-group-addon {\r
+ color: #d9534f;\r
+ border-color: #d9534f;\r
+ background-color: #f2dede;\r
+}\r
+.has-error .form-control-feedback {\r
+ color: #d9534f;\r
+}\r
+.form-control-static {\r
+ margin-bottom: 0;\r
+}\r
+.help-block {\r
+ display: block;\r
+ margin-top: 5px;\r
+ margin-bottom: 10px;\r
+ color: #737373;\r
+}\r
+@media (min-width: 768px) {\r
+ .form-inline .form-group {\r
+ display: inline-block;\r
+ margin-bottom: 0;\r
+ vertical-align: middle;\r
+ }\r
+ .form-inline .form-control {\r
+ display: inline-block;\r
+ width: auto;\r
+ vertical-align: middle;\r
+ }\r
+ .form-inline .input-group > .form-control {\r
+ width: 100%;\r
+ }\r
+ .form-inline .control-label {\r
+ margin-bottom: 0;\r
+ vertical-align: middle;\r
+ }\r
+ .form-inline .radio,\r
+ .form-inline .checkbox {\r
+ display: inline-block;\r
+ margin-top: 0;\r
+ margin-bottom: 0;\r
+ padding-left: 0;\r
+ vertical-align: middle;\r
+ }\r
+ .form-inline .radio input[type="radio"],\r
+ .form-inline .checkbox input[type="checkbox"] {\r
+ float: none;\r
+ margin-left: 0;\r
+ }\r
+ .form-inline .has-feedback .form-control-feedback {\r
+ top: 0;\r
+ }\r
+}\r
+.form-horizontal .control-label,\r
+.form-horizontal .radio,\r
+.form-horizontal .checkbox,\r
+.form-horizontal .radio-inline,\r
+.form-horizontal .checkbox-inline {\r
+ margin-top: 0;\r
+ margin-bottom: 0;\r
+ padding-top: 7px;\r
+}\r
+.form-horizontal .radio,\r
+.form-horizontal .checkbox {\r
+ min-height: 27px;\r
+}\r
+.form-horizontal .form-group {\r
+ margin-left: -15px;\r
+ margin-right: -15px;\r
+}\r
+.form-horizontal .form-control-static {\r
+ padding-top: 7px;\r
+}\r
+@media (min-width: 768px) {\r
+ .form-horizontal .control-label {\r
+ text-align: right;\r
+ }\r
+}\r
+.form-horizontal .has-feedback .form-control-feedback {\r
+ top: 0;\r
+ right: 15px;\r
+}\r
+.btn {\r
+ display: inline-block;\r
+ margin-bottom: 0;\r
+ font-weight: normal;\r
+ text-align: center;\r
+ vertical-align: middle;\r
+ cursor: pointer;\r
+ background-image: none;\r
+ border: 1px solid transparent;\r
+ white-space: nowrap;\r
+ padding: 6px 12px;\r
+ font-size: 14px;\r
+ line-height: 1.428571429;\r
+ border-radius: 0px;\r
+ -webkit-user-select: none;\r
+ -moz-user-select: none;\r
+ -ms-user-select: none;\r
+ -o-user-select: none;\r
+ user-select: none;\r
+}\r
+.btn:focus {\r
+ outline: thin dotted;\r
+ outline: 5px auto -webkit-focus-ring-color;\r
+ outline-offset: -2px;\r
+}\r
+.btn:hover,\r
+.btn:focus {\r
+ color: #333333;\r
+ text-decoration: none;\r
+}\r
+.btn:active,\r
+.btn.active {\r
+ outline: 0;\r
+ background-image: none;\r
+ -webkit-box-shadow: inset 0 3px 5px rgba(0, 0, 0, 0.125);\r
+ box-shadow: inset 0 3px 5px rgba(0, 0, 0, 0.125);\r
+}\r
+.btn.disabled,\r
+.btn[disabled],\r
+fieldset[disabled] .btn {\r
+ cursor: not-allowed;\r
+ pointer-events: none;\r
+ opacity: 0.65;\r
+ filter: alpha(opacity=65);\r
+ -webkit-box-shadow: none;\r
+ box-shadow: none;\r
+}\r
+.btn-default {\r
+ color: #333333;\r
+ background-color: #ffffff;\r
+ border-color: #cccccc;\r
+}\r
+.btn-default:hover,\r
+.btn-default:focus,\r
+.btn-default:active,\r
+.btn-default.active,\r
+.open .dropdown-toggle.btn-default {\r
+ color: #333333;\r
+ background-color: #ebebeb;\r
+ border-color: #adadad;\r
+}\r
+.btn-default:active,\r
+.btn-default.active,\r
+.open .dropdown-toggle.btn-default {\r
+ background-image: none;\r
+}\r
+.btn-default.disabled,\r
+.btn-default[disabled],\r
+fieldset[disabled] .btn-default,\r
+.btn-default.disabled:hover,\r
+.btn-default[disabled]:hover,\r
+fieldset[disabled] .btn-default:hover,\r
+.btn-default.disabled:focus,\r
+.btn-default[disabled]:focus,\r
+fieldset[disabled] .btn-default:focus,\r
+.btn-default.disabled:active,\r
+.btn-default[disabled]:active,\r
+fieldset[disabled] .btn-default:active,\r
+.btn-default.disabled.active,\r
+.btn-default[disabled].active,\r
+fieldset[disabled] .btn-default.active {\r
+ background-color: #ffffff;\r
+ border-color: #cccccc;\r
+}\r
+.btn-default .badge {\r
+ color: #ffffff;\r
+ background-color: #333333;\r
+}\r
+.btn-primary {\r
+ color: #ffffff;\r
+ background-color: #0d8921;\r
+ border-color: #0b721b;\r
+}\r
+.btn-primary:hover,\r
+.btn-primary:focus,\r
+.btn-primary:active,\r
+.btn-primary.active,\r
+.open .dropdown-toggle.btn-primary {\r
+ color: #ffffff;\r
+ background-color: #096418;\r
+ border-color: #053a0e;\r
+}\r
+.btn-primary:active,\r
+.btn-primary.active,\r
+.open .dropdown-toggle.btn-primary {\r
+ background-image: none;\r
+}\r
+.btn-primary.disabled,\r
+.btn-primary[disabled],\r
+fieldset[disabled] .btn-primary,\r
+.btn-primary.disabled:hover,\r
+.btn-primary[disabled]:hover,\r
+fieldset[disabled] .btn-primary:hover,\r
+.btn-primary.disabled:focus,\r
+.btn-primary[disabled]:focus,\r
+fieldset[disabled] .btn-primary:focus,\r
+.btn-primary.disabled:active,\r
+.btn-primary[disabled]:active,\r
+fieldset[disabled] .btn-primary:active,\r
+.btn-primary.disabled.active,\r
+.btn-primary[disabled].active,\r
+fieldset[disabled] .btn-primary.active {\r
+ background-color: #0d8921;\r
+ border-color: #0b721b;\r
+}\r
+.btn-primary .badge {\r
+ color: #0d8921;\r
+ background-color: #ffffff;\r
+}\r
+.btn-success {\r
+ color: #ffffff;\r
+ background-color: #5cb85c;\r
+ border-color: #4cae4c;\r
+}\r
+.btn-success:hover,\r
+.btn-success:focus,\r
+.btn-success:active,\r
+.btn-success.active,\r
+.open .dropdown-toggle.btn-success {\r
+ color: #ffffff;\r
+ background-color: #47a447;\r
+ border-color: #398439;\r
+}\r
+.btn-success:active,\r
+.btn-success.active,\r
+.open .dropdown-toggle.btn-success {\r
+ background-image: none;\r
+}\r
+.btn-success.disabled,\r
+.btn-success[disabled],\r
+fieldset[disabled] .btn-success,\r
+.btn-success.disabled:hover,\r
+.btn-success[disabled]:hover,\r
+fieldset[disabled] .btn-success:hover,\r
+.btn-success.disabled:focus,\r
+.btn-success[disabled]:focus,\r
+fieldset[disabled] .btn-success:focus,\r
+.btn-success.disabled:active,\r
+.btn-success[disabled]:active,\r
+fieldset[disabled] .btn-success:active,\r
+.btn-success.disabled.active,\r
+.btn-success[disabled].active,\r
+fieldset[disabled] .btn-success.active {\r
+ background-color: #5cb85c;\r
+ border-color: #4cae4c;\r
+}\r
+.btn-success .badge {\r
+ color: #5cb85c;\r
+ background-color: #ffffff;\r
+}\r
+.btn-info {\r
+ color: #ffffff;\r
+ background-color: #5bc0de;\r
+ border-color: #46b8da;\r
+}\r
+.btn-info:hover,\r
+.btn-info:focus,\r
+.btn-info:active,\r
+.btn-info.active,\r
+.open .dropdown-toggle.btn-info {\r
+ color: #ffffff;\r
+ background-color: #39b3d7;\r
+ border-color: #269abc;\r
+}\r
+.btn-info:active,\r
+.btn-info.active,\r
+.open .dropdown-toggle.btn-info {\r
+ background-image: none;\r
+}\r
+.btn-info.disabled,\r
+.btn-info[disabled],\r
+fieldset[disabled] .btn-info,\r
+.btn-info.disabled:hover,\r
+.btn-info[disabled]:hover,\r
+fieldset[disabled] .btn-info:hover,\r
+.btn-info.disabled:focus,\r
+.btn-info[disabled]:focus,\r
+fieldset[disabled] .btn-info:focus,\r
+.btn-info.disabled:active,\r
+.btn-info[disabled]:active,\r
+fieldset[disabled] .btn-info:active,\r
+.btn-info.disabled.active,\r
+.btn-info[disabled].active,\r
+fieldset[disabled] .btn-info.active {\r
+ background-color: #5bc0de;\r
+ border-color: #46b8da;\r
+}\r
+.btn-info .badge {\r
+ color: #5bc0de;\r
+ background-color: #ffffff;\r
+}\r
+.btn-warning {\r
+ color: #ffffff;\r
+ background-color: #f0ad4e;\r
+ border-color: #eea236;\r
+}\r
+.btn-warning:hover,\r
+.btn-warning:focus,\r
+.btn-warning:active,\r
+.btn-warning.active,\r
+.open .dropdown-toggle.btn-warning {\r
+ color: #ffffff;\r
+ background-color: #ed9c28;\r
+ border-color: #d58512;\r
+}\r
+.btn-warning:active,\r
+.btn-warning.active,\r
+.open .dropdown-toggle.btn-warning {\r
+ background-image: none;\r
+}\r
+.btn-warning.disabled,\r
+.btn-warning[disabled],\r
+fieldset[disabled] .btn-warning,\r
+.btn-warning.disabled:hover,\r
+.btn-warning[disabled]:hover,\r
+fieldset[disabled] .btn-warning:hover,\r
+.btn-warning.disabled:focus,\r
+.btn-warning[disabled]:focus,\r
+fieldset[disabled] .btn-warning:focus,\r
+.btn-warning.disabled:active,\r
+.btn-warning[disabled]:active,\r
+fieldset[disabled] .btn-warning:active,\r
+.btn-warning.disabled.active,\r
+.btn-warning[disabled].active,\r
+fieldset[disabled] .btn-warning.active {\r
+ background-color: #f0ad4e;\r
+ border-color: #eea236;\r
+}\r
+.btn-warning .badge {\r
+ color: #f0ad4e;\r
+ background-color: #ffffff;\r
+}\r
+.btn-danger {\r
+ color: #ffffff;\r
+ background-color: #d9534f;\r
+ border-color: #d43f3a;\r
+}\r
+.btn-danger:hover,\r
+.btn-danger:focus,\r
+.btn-danger:active,\r
+.btn-danger.active,\r
+.open .dropdown-toggle.btn-danger {\r
+ color: #ffffff;\r
+ background-color: #d2322d;\r
+ border-color: #ac2925;\r
+}\r
+.btn-danger:active,\r
+.btn-danger.active,\r
+.open .dropdown-toggle.btn-danger {\r
+ background-image: none;\r
+}\r
+.btn-danger.disabled,\r
+.btn-danger[disabled],\r
+fieldset[disabled] .btn-danger,\r
+.btn-danger.disabled:hover,\r
+.btn-danger[disabled]:hover,\r
+fieldset[disabled] .btn-danger:hover,\r
+.btn-danger.disabled:focus,\r
+.btn-danger[disabled]:focus,\r
+fieldset[disabled] .btn-danger:focus,\r
+.btn-danger.disabled:active,\r
+.btn-danger[disabled]:active,\r
+fieldset[disabled] .btn-danger:active,\r
+.btn-danger.disabled.active,\r
+.btn-danger[disabled].active,\r
+fieldset[disabled] .btn-danger.active {\r
+ background-color: #d9534f;\r
+ border-color: #d43f3a;\r
+}\r
+.btn-danger .badge {\r
+ color: #d9534f;\r
+ background-color: #ffffff;\r
+}\r
+.btn-link {\r
+ color: #0d8921;\r
+ font-weight: normal;\r
+ cursor: pointer;\r
+ border-radius: 0;\r
+}\r
+.btn-link,\r
+.btn-link:active,\r
+.btn-link[disabled],\r
+fieldset[disabled] .btn-link {\r
+ background-color: transparent;\r
+ -webkit-box-shadow: none;\r
+ box-shadow: none;\r
+}\r
+.btn-link,\r
+.btn-link:hover,\r
+.btn-link:focus,\r
+.btn-link:active {\r
+ border-color: transparent;\r
+}\r
+.btn-link:hover,\r
+.btn-link:focus {\r
+ color: #064310;\r
+ text-decoration: underline;\r
+ background-color: transparent;\r
+}\r
+.btn-link[disabled]:hover,\r
+fieldset[disabled] .btn-link:hover,\r
+.btn-link[disabled]:focus,\r
+fieldset[disabled] .btn-link:focus {\r
+ color: #999999;\r
+ text-decoration: none;\r
+}\r
+.btn-lg,\r
+.btn-group-lg > .btn {\r
+ padding: 10px 16px;\r
+ font-size: 18px;\r
+ line-height: 1.33;\r
+ border-radius: 0px;\r
+}\r
+.btn-sm,\r
+.btn-group-sm > .btn {\r
+ padding: 5px 10px;\r
+ font-size: 12px;\r
+ line-height: 1.5;\r
+ border-radius: 0px;\r
+}\r
+.btn-xs,\r
+.btn-group-xs > .btn {\r
+ padding: 1px 5px;\r
+ font-size: 12px;\r
+ line-height: 1.5;\r
+ border-radius: 0px;\r
+}\r
+.btn-block {\r
+ display: block;\r
+ width: 100%;\r
+ padding-left: 0;\r
+ padding-right: 0;\r
+}\r
+.btn-block + .btn-block {\r
+ margin-top: 5px;\r
+}\r
+input[type="submit"].btn-block,\r
+input[type="reset"].btn-block,\r
+input[type="button"].btn-block {\r
+ width: 100%;\r
+}\r
+.fade {\r
+ opacity: 0;\r
+ -webkit-transition: opacity 0.15s linear;\r
+ transition: opacity 0.15s linear;\r
+}\r
+.fade.in {\r
+ opacity: 1;\r
+}\r
+.collapse {\r
+ display: none;\r
+}\r
+.collapse.in {\r
+ display: block;\r
+}\r
+.collapsing {\r
+ position: relative;\r
+ height: 0;\r
+ overflow: hidden;\r
+ -webkit-transition: height 0.35s ease;\r
+ transition: height 0.35s ease;\r
+}\r
+@font-face {\r
+ font-family: 'Glyphicons Halflings';\r
+ src: url('https://maxcdn.bootstrapcdn.com/bootstrap/3.3.6/fonts/glyphicons-halflings-regular.eot');\r
+ src: url('https://maxcdn.bootstrapcdn.com/bootstrap/3.3.6/fonts/glyphicons-halflings-regular.eot?#iefix') format('embedded-opentype'), url('https://maxcdn.bootstrapcdn.com/bootstrap/3.3.6/fonts/glyphicons-halflings-regular.woff') format('woff'), url('https://maxcdn.bootstrapcdn.com/bootstrap/3.3.6/fonts/glyphicons-halflings-regular.ttf') format('truetype'), url('https://maxcdn.bootstrapcdn.com/bootstrap/3.3.6/fonts/glyphicons-halflings-regular.svg#glyphicons_halflingsregular') format('svg');\r
+}\r
+.glyphicon {\r
+ position: relative;\r
+ top: 1px;\r
+ display: inline-block;\r
+ font-family: 'Glyphicons Halflings';\r
+ font-style: normal;\r
+ font-weight: normal;\r
+ line-height: 1;\r
+ -webkit-font-smoothing: antialiased;\r
+ -moz-osx-font-smoothing: grayscale;\r
+}\r
+.glyphicon-asterisk:before {\r
+ content: "\2a";\r
+}\r
+.glyphicon-plus:before {\r
+ content: "\2b";\r
+}\r
+.glyphicon-euro:before {\r
+ content: "\20ac";\r
+}\r
+.glyphicon-minus:before {\r
+ content: "\2212";\r
+}\r
+.glyphicon-cloud:before {\r
+ content: "\2601";\r
+}\r
+.glyphicon-envelope:before {\r
+ content: "\2709";\r
+}\r
+.glyphicon-pencil:before {\r
+ content: "\270f";\r
+}\r
+.glyphicon-glass:before {\r
+ content: "\e001";\r
+}\r
+.glyphicon-music:before {\r
+ content: "\e002";\r
+}\r
+.glyphicon-search:before {\r
+ content: "\e003";\r
+}\r
+.glyphicon-heart:before {\r
+ content: "\e005";\r
+}\r
+.glyphicon-star:before {\r
+ content: "\e006";\r
+}\r
+.glyphicon-star-empty:before {\r
+ content: "\e007";\r
+}\r
+.glyphicon-user:before {\r
+ content: "\e008";\r
+}\r
+.glyphicon-film:before {\r
+ content: "\e009";\r
+}\r
+.glyphicon-th-large:before {\r
+ content: "\e010";\r
+}\r
+.glyphicon-th:before {\r
+ content: "\e011";\r
+}\r
+.glyphicon-th-list:before {\r
+ content: "\e012";\r
+}\r
+.glyphicon-ok:before {\r
+ content: "\e013";\r
+}\r
+.glyphicon-remove:before {\r
+ content: "\e014";\r
+}\r
+.glyphicon-zoom-in:before {\r
+ content: "\e015";\r
+}\r
+.glyphicon-zoom-out:before {\r
+ content: "\e016";\r
+}\r
+.glyphicon-off:before {\r
+ content: "\e017";\r
+}\r
+.glyphicon-signal:before {\r
+ content: "\e018";\r
+}\r
+.glyphicon-cog:before {\r
+ content: "\e019";\r
+}\r
+.glyphicon-trash:before {\r
+ content: "\e020";\r
+}\r
+.glyphicon-home:before {\r
+ content: "\e021";\r
+}\r
+.glyphicon-file:before {\r
+ content: "\e022";\r
+}\r
+.glyphicon-time:before {\r
+ content: "\e023";\r
+}\r
+.glyphicon-road:before {\r
+ content: "\e024";\r
+}\r
+.glyphicon-download-alt:before {\r
+ content: "\e025";\r
+}\r
+.glyphicon-download:before {\r
+ content: "\e026";\r
+}\r
+.glyphicon-upload:before {\r
+ content: "\e027";\r
+}\r
+.glyphicon-inbox:before {\r
+ content: "\e028";\r
+}\r
+.glyphicon-play-circle:before {\r
+ content: "\e029";\r
+}\r
+.glyphicon-repeat:before {\r
+ content: "\e030";\r
+}\r
+.glyphicon-refresh:before {\r
+ content: "\e031";\r
+}\r
+.glyphicon-list-alt:before {\r
+ content: "\e032";\r
+}\r
+.glyphicon-lock:before {\r
+ content: "\e033";\r
+}\r
+.glyphicon-flag:before {\r
+ content: "\e034";\r
+}\r
+.glyphicon-headphones:before {\r
+ content: "\e035";\r
+}\r
+.glyphicon-volume-off:before {\r
+ content: "\e036";\r
+}\r
+.glyphicon-volume-down:before {\r
+ content: "\e037";\r
+}\r
+.glyphicon-volume-up:before {\r
+ content: "\e038";\r
+}\r
+.glyphicon-qrcode:before {\r
+ content: "\e039";\r
+}\r
+.glyphicon-barcode:before {\r
+ content: "\e040";\r
+}\r
+.glyphicon-tag:before {\r
+ content: "\e041";\r
+}\r
+.glyphicon-tags:before {\r
+ content: "\e042";\r
+}\r
+.glyphicon-book:before {\r
+ content: "\e043";\r
+}\r
+.glyphicon-bookmark:before {\r
+ content: "\e044";\r
+}\r
+.glyphicon-print:before {\r
+ content: "\e045";\r
+}\r
+.glyphicon-camera:before {\r
+ content: "\e046";\r
+}\r
+.glyphicon-font:before {\r
+ content: "\e047";\r
+}\r
+.glyphicon-bold:before {\r
+ content: "\e048";\r
+}\r
+.glyphicon-italic:before {\r
+ content: "\e049";\r
+}\r
+.glyphicon-text-height:before {\r
+ content: "\e050";\r
+}\r
+.glyphicon-text-width:before {\r
+ content: "\e051";\r
+}\r
+.glyphicon-align-left:before {\r
+ content: "\e052";\r
+}\r
+.glyphicon-align-center:before {\r
+ content: "\e053";\r
+}\r
+.glyphicon-align-right:before {\r
+ content: "\e054";\r
+}\r
+.glyphicon-align-justify:before {\r
+ content: "\e055";\r
+}\r
+.glyphicon-list:before {\r
+ content: "\e056";\r
+}\r
+.glyphicon-indent-left:before {\r
+ content: "\e057";\r
+}\r
+.glyphicon-indent-right:before {\r
+ content: "\e058";\r
+}\r
+.glyphicon-facetime-video:before {\r
+ content: "\e059";\r
+}\r
+.glyphicon-picture:before {\r
+ content: "\e060";\r
+}\r
+.glyphicon-map-marker:before {\r
+ content: "\e062";\r
+}\r
+.glyphicon-adjust:before {\r
+ content: "\e063";\r
+}\r
+.glyphicon-tint:before {\r
+ content: "\e064";\r
+}\r
+.glyphicon-edit:before {\r
+ content: "\e065";\r
+}\r
+.glyphicon-share:before {\r
+ content: "\e066";\r
+}\r
+.glyphicon-check:before {\r
+ content: "\e067";\r
+}\r
+.glyphicon-move:before {\r
+ content: "\e068";\r
+}\r
+.glyphicon-step-backward:before {\r
+ content: "\e069";\r
+}\r
+.glyphicon-fast-backward:before {\r
+ content: "\e070";\r
+}\r
+.glyphicon-backward:before {\r
+ content: "\e071";\r
+}\r
+.glyphicon-play:before {\r
+ content: "\e072";\r
+}\r
+.glyphicon-pause:before {\r
+ content: "\e073";\r
+}\r
+.glyphicon-stop:before {\r
+ content: "\e074";\r
+}\r
+.glyphicon-forward:before {\r
+ content: "\e075";\r
+}\r
+.glyphicon-fast-forward:before {\r
+ content: "\e076";\r
+}\r
+.glyphicon-step-forward:before {\r
+ content: "\e077";\r
+}\r
+.glyphicon-eject:before {\r
+ content: "\e078";\r
+}\r
+.glyphicon-chevron-left:before {\r
+ content: "\e079";\r
+}\r
+.glyphicon-chevron-right:before {\r
+ content: "\e080";\r
+}\r
+.glyphicon-plus-sign:before {\r
+ content: "\e081";\r
+}\r
+.glyphicon-minus-sign:before {\r
+ content: "\e082";\r
+}\r
+.glyphicon-remove-sign:before {\r
+ content: "\e083";\r
+}\r
+.glyphicon-ok-sign:before {\r
+ content: "\e084";\r
+}\r
+.glyphicon-question-sign:before {\r
+ content: "\e085";\r
+}\r
+.glyphicon-info-sign:before {\r
+ content: "\e086";\r
+}\r
+.glyphicon-screenshot:before {\r
+ content: "\e087";\r
+}\r
+.glyphicon-remove-circle:before {\r
+ content: "\e088";\r
+}\r
+.glyphicon-ok-circle:before {\r
+ content: "\e089";\r
+}\r
+.glyphicon-ban-circle:before {\r
+ content: "\e090";\r
+}\r
+.glyphicon-arrow-left:before {\r
+ content: "\e091";\r
+}\r
+.glyphicon-arrow-right:before {\r
+ content: "\e092";\r
+}\r
+.glyphicon-arrow-up:before {\r
+ content: "\e093";\r
+}\r
+.glyphicon-arrow-down:before {\r
+ content: "\e094";\r
+}\r
+.glyphicon-share-alt:before {\r
+ content: "\e095";\r
+}\r
+.glyphicon-resize-full:before {\r
+ content: "\e096";\r
+}\r
+.glyphicon-resize-small:before {\r
+ content: "\e097";\r
+}\r
+.glyphicon-exclamation-sign:before {\r
+ content: "\e101";\r
+}\r
+.glyphicon-gift:before {\r
+ content: "\e102";\r
+}\r
+.glyphicon-leaf:before {\r
+ content: "\e103";\r
+}\r
+.glyphicon-fire:before {\r
+ content: "\e104";\r
+}\r
+.glyphicon-eye-open:before {\r
+ content: "\e105";\r
+}\r
+.glyphicon-eye-close:before {\r
+ content: "\e106";\r
+}\r
+.glyphicon-warning-sign:before {\r
+ content: "\e107";\r
+}\r
+.glyphicon-plane:before {\r
+ content: "\e108";\r
+}\r
+.glyphicon-calendar:before {\r
+ content: "\e109";\r
+}\r
+.glyphicon-random:before {\r
+ content: "\e110";\r
+}\r
+.glyphicon-comment:before {\r
+ content: "\e111";\r
+}\r
+.glyphicon-magnet:before {\r
+ content: "\e112";\r
+}\r
+.glyphicon-chevron-up:before {\r
+ content: "\e113";\r
+}\r
+.glyphicon-chevron-down:before {\r
+ content: "\e114";\r
+}\r
+.glyphicon-retweet:before {\r
+ content: "\e115";\r
+}\r
+.glyphicon-shopping-cart:before {\r
+ content: "\e116";\r
+}\r
+.glyphicon-folder-close:before {\r
+ content: "\e117";\r
+}\r
+.glyphicon-folder-open:before {\r
+ content: "\e118";\r
+}\r
+.glyphicon-resize-vertical:before {\r
+ content: "\e119";\r
+}\r
+.glyphicon-resize-horizontal:before {\r
+ content: "\e120";\r
+}\r
+.glyphicon-hdd:before {\r
+ content: "\e121";\r
+}\r
+.glyphicon-bullhorn:before {\r
+ content: "\e122";\r
+}\r
+.glyphicon-bell:before {\r
+ content: "\e123";\r
+}\r
+.glyphicon-certificate:before {\r
+ content: "\e124";\r
+}\r
+.glyphicon-thumbs-up:before {\r
+ content: "\e125";\r
+}\r
+.glyphicon-thumbs-down:before {\r
+ content: "\e126";\r
+}\r
+.glyphicon-hand-right:before {\r
+ content: "\e127";\r
+}\r
+.glyphicon-hand-left:before {\r
+ content: "\e128";\r
+}\r
+.glyphicon-hand-up:before {\r
+ content: "\e129";\r
+}\r
+.glyphicon-hand-down:before {\r
+ content: "\e130";\r
+}\r
+.glyphicon-circle-arrow-right:before {\r
+ content: "\e131";\r
+}\r
+.glyphicon-circle-arrow-left:before {\r
+ content: "\e132";\r
+}\r
+.glyphicon-circle-arrow-up:before {\r
+ content: "\e133";\r
+}\r
+.glyphicon-circle-arrow-down:before {\r
+ content: "\e134";\r
+}\r
+.glyphicon-globe:before {\r
+ content: "\e135";\r
+}\r
+.glyphicon-wrench:before {\r
+ content: "\e136";\r
+}\r
+.glyphicon-tasks:before {\r
+ content: "\e137";\r
+}\r
+.glyphicon-filter:before {\r
+ content: "\e138";\r
+}\r
+.glyphicon-briefcase:before {\r
+ content: "\e139";\r
+}\r
+.glyphicon-fullscreen:before {\r
+ content: "\e140";\r
+}\r
+.glyphicon-dashboard:before {\r
+ content: "\e141";\r
+}\r
+.glyphicon-paperclip:before {\r
+ content: "\e142";\r
+}\r
+.glyphicon-heart-empty:before {\r
+ content: "\e143";\r
+}\r
+.glyphicon-link:before {\r
+ content: "\e144";\r
+}\r
+.glyphicon-phone:before {\r
+ content: "\e145";\r
+}\r
+.glyphicon-pushpin:before {\r
+ content: "\e146";\r
+}\r
+.glyphicon-usd:before {\r
+ content: "\e148";\r
+}\r
+.glyphicon-gbp:before {\r
+ content: "\e149";\r
+}\r
+.glyphicon-sort:before {\r
+ content: "\e150";\r
+}\r
+.glyphicon-sort-by-alphabet:before {\r
+ content: "\e151";\r
+}\r
+.glyphicon-sort-by-alphabet-alt:before {\r
+ content: "\e152";\r
+}\r
+.glyphicon-sort-by-order:before {\r
+ content: "\e153";\r
+}\r
+.glyphicon-sort-by-order-alt:before {\r
+ content: "\e154";\r
+}\r
+.glyphicon-sort-by-attributes:before {\r
+ content: "\e155";\r
+}\r
+.glyphicon-sort-by-attributes-alt:before {\r
+ content: "\e156";\r
+}\r
+.glyphicon-unchecked:before {\r
+ content: "\e157";\r
+}\r
+.glyphicon-expand:before {\r
+ content: "\e158";\r
+}\r
+.glyphicon-collapse-down:before {\r
+ content: "\e159";\r
+}\r
+.glyphicon-collapse-up:before {\r
+ content: "\e160";\r
+}\r
+.glyphicon-log-in:before {\r
+ content: "\e161";\r
+}\r
+.glyphicon-flash:before {\r
+ content: "\e162";\r
+}\r
+.glyphicon-log-out:before {\r
+ content: "\e163";\r
+}\r
+.glyphicon-new-window:before {\r
+ content: "\e164";\r
+}\r
+.glyphicon-record:before {\r
+ content: "\e165";\r
+}\r
+.glyphicon-save:before {\r
+ content: "\e166";\r
+}\r
+.glyphicon-open:before {\r
+ content: "\e167";\r
+}\r
+.glyphicon-saved:before {\r
+ content: "\e168";\r
+}\r
+.glyphicon-import:before {\r
+ content: "\e169";\r
+}\r
+.glyphicon-export:before {\r
+ content: "\e170";\r
+}\r
+.glyphicon-send:before {\r
+ content: "\e171";\r
+}\r
+.glyphicon-floppy-disk:before {\r
+ content: "\e172";\r
+}\r
+.glyphicon-floppy-saved:before {\r
+ content: "\e173";\r
+}\r
+.glyphicon-floppy-remove:before {\r
+ content: "\e174";\r
+}\r
+.glyphicon-floppy-save:before {\r
+ content: "\e175";\r
+}\r
+.glyphicon-floppy-open:before {\r
+ content: "\e176";\r
+}\r
+.glyphicon-credit-card:before {\r
+ content: "\e177";\r
+}\r
+.glyphicon-transfer:before {\r
+ content: "\e178";\r
+}\r
+.glyphicon-cutlery:before {\r
+ content: "\e179";\r
+}\r
+.glyphicon-header:before {\r
+ content: "\e180";\r
+}\r
+.glyphicon-compressed:before {\r
+ content: "\e181";\r
+}\r
+.glyphicon-earphone:before {\r
+ content: "\e182";\r
+}\r
+.glyphicon-phone-alt:before {\r
+ content: "\e183";\r
+}\r
+.glyphicon-tower:before {\r
+ content: "\e184";\r
+}\r
+.glyphicon-stats:before {\r
+ content: "\e185";\r
+}\r
+.glyphicon-sd-video:before {\r
+ content: "\e186";\r
+}\r
+.glyphicon-hd-video:before {\r
+ content: "\e187";\r
+}\r
+.glyphicon-subtitles:before {\r
+ content: "\e188";\r
+}\r
+.glyphicon-sound-stereo:before {\r
+ content: "\e189";\r
+}\r
+.glyphicon-sound-dolby:before {\r
+ content: "\e190";\r
+}\r
+.glyphicon-sound-5-1:before {\r
+ content: "\e191";\r
+}\r
+.glyphicon-sound-6-1:before {\r
+ content: "\e192";\r
+}\r
+.glyphicon-sound-7-1:before {\r
+ content: "\e193";\r
+}\r
+.glyphicon-copyright-mark:before {\r
+ content: "\e194";\r
+}\r
+.glyphicon-registration-mark:before {\r
+ content: "\e195";\r
+}\r
+.glyphicon-cloud-download:before {\r
+ content: "\e197";\r
+}\r
+.glyphicon-cloud-upload:before {\r
+ content: "\e198";\r
+}\r
+.glyphicon-tree-conifer:before {\r
+ content: "\e199";\r
+}\r
+.glyphicon-tree-deciduous:before {\r
+ content: "\e200";\r
+}\r
+.caret {\r
+ display: inline-block;\r
+ width: 0;\r
+ height: 0;\r
+ margin-left: 2px;\r
+ vertical-align: middle;\r
+ border-top: 4px solid;\r
+ border-right: 4px solid transparent;\r
+ border-left: 4px solid transparent;\r
+}\r
+.dropdown {\r
+ position: relative;\r
+}\r
+.dropdown-toggle:focus {\r
+ outline: 0;\r
+}\r
+.dropdown-menu {\r
+ position: absolute;\r
+ top: 100%;\r
+ left: 0;\r
+ z-index: 1000;\r
+ display: none;\r
+ float: left;\r
+ min-width: 160px;\r
+ padding: 5px 0;\r
+ margin: 2px 0 0;\r
+ list-style: none;\r
+ font-size: 14px;\r
+ background-color: #ffffff;\r
+ border: 1px solid #cccccc;\r
+ border: 1px solid rgba(0, 0, 0, 0.15);\r
+ border-radius: 0px;\r
+ -webkit-box-shadow: 0 6px 12px rgba(0, 0, 0, 0.175);\r
+ box-shadow: 0 6px 12px rgba(0, 0, 0, 0.175);\r
+ background-clip: padding-box;\r
+}\r
+.dropdown-menu.pull-right {\r
+ right: 0;\r
+ left: auto;\r
+}\r
+.dropdown-menu .divider {\r
+ height: 1px;\r
+ margin: 9px 0;\r
+ overflow: hidden;\r
+ background-color: #e5e5e5;\r
+}\r
+.dropdown-menu > li > a {\r
+ display: block;\r
+ padding: 3px 20px;\r
+ clear: both;\r
+ font-weight: normal;\r
+ line-height: 1.428571429;\r
+ color: #333333;\r
+ white-space: nowrap;\r
+}\r
+.dropdown-menu > li > a:hover,\r
+.dropdown-menu > li > a:focus {\r
+ text-decoration: none;\r
+ color: #ffffff;\r
+ background-color: #0d8921;\r
+}\r
+.dropdown-menu > .active > a,\r
+.dropdown-menu > .active > a:hover,\r
+.dropdown-menu > .active > a:focus {\r
+ color: #ffffff;\r
+ text-decoration: none;\r
+ outline: 0;\r
+ background-color: #0d8921;\r
+}\r
+.dropdown-menu > .disabled > a,\r
+.dropdown-menu > .disabled > a:hover,\r
+.dropdown-menu > .disabled > a:focus {\r
+ color: #999999;\r
+}\r
+.dropdown-menu > .disabled > a:hover,\r
+.dropdown-menu > .disabled > a:focus {\r
+ text-decoration: none;\r
+ background-color: transparent;\r
+ background-image: none;\r
+ filter: progid:DXImageTransform.Microsoft.gradient(enabled = false);\r
+ cursor: not-allowed;\r
+}\r
+.open > .dropdown-menu {\r
+ display: block;\r
+}\r
+.open > a {\r
+ outline: 0;\r
+}\r
+.dropdown-menu-right {\r
+ left: auto;\r
+ right: 0;\r
+}\r
+.dropdown-menu-left {\r
+ left: 0;\r
+ right: auto;\r
+}\r
+.dropdown-header {\r
+ display: block;\r
+ padding: 3px 20px;\r
+ font-size: 12px;\r
+ line-height: 1.428571429;\r
+ color: #999999;\r
+}\r
+.dropdown-backdrop {\r
+ position: fixed;\r
+ left: 0;\r
+ right: 0;\r
+ bottom: 0;\r
+ top: 0;\r
+ z-index: 990;\r
+}\r
+.pull-right > .dropdown-menu {\r
+ right: 0;\r
+ left: auto;\r
+}\r
+.dropup .caret,\r
+.navbar-fixed-bottom .dropdown .caret {\r
+ border-top: 0;\r
+ border-bottom: 4px solid;\r
+ content: "";\r
+}\r
+.dropup .dropdown-menu,\r
+.navbar-fixed-bottom .dropdown .dropdown-menu {\r
+ top: auto;\r
+ bottom: 100%;\r
+ margin-bottom: 1px;\r
+}\r
+@media (min-width: 768px) {\r
+ .navbar-right .dropdown-menu {\r
+ left: auto;\r
+ right: 0;\r
+ }\r
+ .navbar-right .dropdown-menu-left {\r
+ left: 0;\r
+ right: auto;\r
+ }\r
+}\r
+.btn-group,\r
+.btn-group-vertical {\r
+ position: relative;\r
+ display: inline-block;\r
+ vertical-align: middle;\r
+}\r
+.btn-group > .btn,\r
+.btn-group-vertical > .btn {\r
+ position: relative;\r
+ float: left;\r
+}\r
+.btn-group > .btn:hover,\r
+.btn-group-vertical > .btn:hover,\r
+.btn-group > .btn:focus,\r
+.btn-group-vertical > .btn:focus,\r
+.btn-group > .btn:active,\r
+.btn-group-vertical > .btn:active,\r
+.btn-group > .btn.active,\r
+.btn-group-vertical > .btn.active {\r
+ z-index: 2;\r
+}\r
+.btn-group > .btn:focus,\r
+.btn-group-vertical > .btn:focus {\r
+ outline: none;\r
+}\r
+.btn-group .btn + .btn,\r
+.btn-group .btn + .btn-group,\r
+.btn-group .btn-group + .btn,\r
+.btn-group .btn-group + .btn-group {\r
+ margin-left: -1px;\r
+}\r
+.btn-toolbar {\r
+ margin-left: -5px;\r
+}\r
+.btn-toolbar .btn-group,\r
+.btn-toolbar .input-group {\r
+ float: left;\r
+}\r
+.btn-toolbar > .btn,\r
+.btn-toolbar > .btn-group,\r
+.btn-toolbar > .input-group {\r
+ margin-left: 5px;\r
+}\r
+.btn-group > .btn:not(:first-child):not(:last-child):not(.dropdown-toggle) {\r
+ border-radius: 0;\r
+}\r
+.btn-group > .btn:first-child {\r
+ margin-left: 0;\r
+}\r
+.btn-group > .btn:first-child:not(:last-child):not(.dropdown-toggle) {\r
+ border-bottom-right-radius: 0;\r
+ border-top-right-radius: 0;\r
+}\r
+.btn-group > .btn:last-child:not(:first-child),\r
+.btn-group > .dropdown-toggle:not(:first-child) {\r
+ border-bottom-left-radius: 0;\r
+ border-top-left-radius: 0;\r
+}\r
+.btn-group > .btn-group {\r
+ float: left;\r
+}\r
+.btn-group > .btn-group:not(:first-child):not(:last-child) > .btn {\r
+ border-radius: 0;\r
+}\r
+.btn-group > .btn-group:first-child > .btn:last-child,\r
+.btn-group > .btn-group:first-child > .dropdown-toggle {\r
+ border-bottom-right-radius: 0;\r
+ border-top-right-radius: 0;\r
+}\r
+.btn-group > .btn-group:last-child > .btn:first-child {\r
+ border-bottom-left-radius: 0;\r
+ border-top-left-radius: 0;\r
+}\r
+.btn-group .dropdown-toggle:active,\r
+.btn-group.open .dropdown-toggle {\r
+ outline: 0;\r
+}\r
+.btn-group > .btn + .dropdown-toggle {\r
+ padding-left: 8px;\r
+ padding-right: 8px;\r
+}\r
+.btn-group > .btn-lg + .dropdown-toggle {\r
+ padding-left: 12px;\r
+ padding-right: 12px;\r
+}\r
+.btn-group.open .dropdown-toggle {\r
+ -webkit-box-shadow: inset 0 3px 5px rgba(0, 0, 0, 0.125);\r
+ box-shadow: inset 0 3px 5px rgba(0, 0, 0, 0.125);\r
+}\r
+.btn-group.open .dropdown-toggle.btn-link {\r
+ -webkit-box-shadow: none;\r
+ box-shadow: none;\r
+}\r
+.btn .caret {\r
+ margin-left: 0;\r
+}\r
+.btn-lg .caret {\r
+ border-width: 5px 5px 0;\r
+ border-bottom-width: 0;\r
+}\r
+.dropup .btn-lg .caret {\r
+ border-width: 0 5px 5px;\r
+}\r
+.btn-group-vertical > .btn,\r
+.btn-group-vertical > .btn-group,\r
+.btn-group-vertical > .btn-group > .btn {\r
+ display: block;\r
+ float: none;\r
+ width: 100%;\r
+ max-width: 100%;\r
+}\r
+.btn-group-vertical > .btn-group > .btn {\r
+ float: none;\r
+}\r
+.btn-group-vertical > .btn + .btn,\r
+.btn-group-vertical > .btn + .btn-group,\r
+.btn-group-vertical > .btn-group + .btn,\r
+.btn-group-vertical > .btn-group + .btn-group {\r
+ margin-top: -1px;\r
+ margin-left: 0;\r
+}\r
+.btn-group-vertical > .btn:not(:first-child):not(:last-child) {\r
+ border-radius: 0;\r
+}\r
+.btn-group-vertical > .btn:first-child:not(:last-child) {\r
+ border-top-right-radius: 0px;\r
+ border-bottom-right-radius: 0;\r
+ border-bottom-left-radius: 0;\r
+}\r
+.btn-group-vertical > .btn:last-child:not(:first-child) {\r
+ border-bottom-left-radius: 0px;\r
+ border-top-right-radius: 0;\r
+ border-top-left-radius: 0;\r
+}\r
+.btn-group-vertical > .btn-group:not(:first-child):not(:last-child) > .btn {\r
+ border-radius: 0;\r
+}\r
+.btn-group-vertical > .btn-group:first-child:not(:last-child) > .btn:last-child,\r
+.btn-group-vertical > .btn-group:first-child:not(:last-child) > .dropdown-toggle {\r
+ border-bottom-right-radius: 0;\r
+ border-bottom-left-radius: 0;\r
+}\r
+.btn-group-vertical > .btn-group:last-child:not(:first-child) > .btn:first-child {\r
+ border-top-right-radius: 0;\r
+ border-top-left-radius: 0;\r
+}\r
+.btn-group-justified {\r
+ display: table;\r
+ width: 100%;\r
+ table-layout: fixed;\r
+ border-collapse: separate;\r
+}\r
+.btn-group-justified > .btn,\r
+.btn-group-justified > .btn-group {\r
+ float: none;\r
+ display: table-cell;\r
+ width: 1%;\r
+}\r
+.btn-group-justified > .btn-group .btn {\r
+ width: 100%;\r
+}\r
+[data-toggle="buttons"] > .btn > input[type="radio"],\r
+[data-toggle="buttons"] > .btn > input[type="checkbox"] {\r
+ display: none;\r
+}\r
+.input-group {\r
+ position: relative;\r
+ display: table;\r
+ border-collapse: separate;\r
+}\r
+.input-group[class*="col-"] {\r
+ float: none;\r
+ padding-left: 0;\r
+ padding-right: 0;\r
+}\r
+.input-group .form-control {\r
+ float: left;\r
+ width: 100%;\r
+ margin-bottom: 0;\r
+}\r
+.input-group-lg > .form-control,\r
+.input-group-lg > .input-group-addon,\r
+.input-group-lg > .input-group-btn > .btn {\r
+ height: 45px;\r
+ padding: 10px 16px;\r
+ font-size: 18px;\r
+ line-height: 1.33;\r
+ border-radius: 0px;\r
+}\r
+select.input-group-lg > .form-control,\r
+select.input-group-lg > .input-group-addon,\r
+select.input-group-lg > .input-group-btn > .btn {\r
+ height: 45px;\r
+ line-height: 45px;\r
+}\r
+textarea.input-group-lg > .form-control,\r
+textarea.input-group-lg > .input-group-addon,\r
+textarea.input-group-lg > .input-group-btn > .btn,\r
+select[multiple].input-group-lg > .form-control,\r
+select[multiple].input-group-lg > .input-group-addon,\r
+select[multiple].input-group-lg > .input-group-btn > .btn {\r
+ height: auto;\r
+}\r
+.input-group-sm > .form-control,\r
+.input-group-sm > .input-group-addon,\r
+.input-group-sm > .input-group-btn > .btn {\r
+ height: 30px;\r
+ padding: 5px 10px;\r
+ font-size: 12px;\r
+ line-height: 1.5;\r
+ border-radius: 0px;\r
+}\r
+select.input-group-sm > .form-control,\r
+select.input-group-sm > .input-group-addon,\r
+select.input-group-sm > .input-group-btn > .btn {\r
+ height: 30px;\r
+ line-height: 30px;\r
+}\r
+textarea.input-group-sm > .form-control,\r
+textarea.input-group-sm > .input-group-addon,\r
+textarea.input-group-sm > .input-group-btn > .btn,\r
+select[multiple].input-group-sm > .form-control,\r
+select[multiple].input-group-sm > .input-group-addon,\r
+select[multiple].input-group-sm > .input-group-btn > .btn {\r
+ height: auto;\r
+}\r
+.input-group-addon,\r
+.input-group-btn,\r
+.input-group .form-control {\r
+ display: table-cell;\r
+}\r
+.input-group-addon:not(:first-child):not(:last-child),\r
+.input-group-btn:not(:first-child):not(:last-child),\r
+.input-group .form-control:not(:first-child):not(:last-child) {\r
+ border-radius: 0;\r
+}\r
+.input-group-addon,\r
+.input-group-btn {\r
+ width: 1%;\r
+ white-space: nowrap;\r
+ vertical-align: middle;\r
+}\r
+.input-group-addon {\r
+ padding: 6px 12px;\r
+ font-size: 14px;\r
+ font-weight: normal;\r
+ line-height: 1;\r
+ color: #555555;\r
+ text-align: center;\r
+ background-color: #eeeeee;\r
+ border: 1px solid #cccccc;\r
+ border-radius: 0px;\r
+}\r
+.input-group-addon.input-sm {\r
+ padding: 5px 10px;\r
+ font-size: 12px;\r
+ border-radius: 0px;\r
+}\r
+.input-group-addon.input-lg {\r
+ padding: 10px 16px;\r
+ font-size: 18px;\r
+ border-radius: 0px;\r
+}\r
+.input-group-addon input[type="radio"],\r
+.input-group-addon input[type="checkbox"] {\r
+ margin-top: 0;\r
+}\r
+.input-group .form-control:first-child,\r
+.input-group-addon:first-child,\r
+.input-group-btn:first-child > .btn,\r
+.input-group-btn:first-child > .btn-group > .btn,\r
+.input-group-btn:first-child > .dropdown-toggle,\r
+.input-group-btn:last-child > .btn:not(:last-child):not(.dropdown-toggle),\r
+.input-group-btn:last-child > .btn-group:not(:last-child) > .btn {\r
+ border-bottom-right-radius: 0;\r
+ border-top-right-radius: 0;\r
+}\r
+.input-group-addon:first-child {\r
+ border-right: 0;\r
+}\r
+.input-group .form-control:last-child,\r
+.input-group-addon:last-child,\r
+.input-group-btn:last-child > .btn,\r
+.input-group-btn:last-child > .btn-group > .btn,\r
+.input-group-btn:last-child > .dropdown-toggle,\r
+.input-group-btn:first-child > .btn:not(:first-child),\r
+.input-group-btn:first-child > .btn-group:not(:first-child) > .btn {\r
+ border-bottom-left-radius: 0;\r
+ border-top-left-radius: 0;\r
+}\r
+.input-group-addon:last-child {\r
+ border-left: 0;\r
+}\r
+.input-group-btn {\r
+ position: relative;\r
+ font-size: 0;\r
+ white-space: nowrap;\r
+}\r
+.input-group-btn > .btn {\r
+ position: relative;\r
+}\r
+.input-group-btn > .btn + .btn {\r
+ margin-left: -1px;\r
+}\r
+.input-group-btn > .btn:hover,\r
+.input-group-btn > .btn:focus,\r
+.input-group-btn > .btn:active {\r
+ z-index: 2;\r
+}\r
+.input-group-btn:first-child > .btn,\r
+.input-group-btn:first-child > .btn-group {\r
+ margin-right: -1px;\r
+}\r
+.input-group-btn:last-child > .btn,\r
+.input-group-btn:last-child > .btn-group {\r
+ margin-left: -1px;\r
+}\r
+.nav {\r
+ margin-bottom: 0;\r
+ padding-left: 0;\r
+ list-style: none;\r
+}\r
+.nav > li {\r
+ position: relative;\r
+ display: block;\r
+}\r
+.nav > li > a {\r
+ position: relative;\r
+ display: block;\r
+ padding: 10px 15px;\r
+}\r
+.nav > li > a:hover,\r
+.nav > li > a:focus {\r
+ text-decoration: none;\r
+ background-color: #dddddd;\r
+}\r
+.nav > li.disabled > a {\r
+ color: #999999;\r
+}\r
+.nav > li.disabled > a:hover,\r
+.nav > li.disabled > a:focus {\r
+ color: #999999;\r
+ text-decoration: none;\r
+ background-color: transparent;\r
+ cursor: not-allowed;\r
+}\r
+.nav .open > a,\r
+.nav .open > a:hover,\r
+.nav .open > a:focus {\r
+ background-color: #dddddd;\r
+ border-color: #0d8921;\r
+}\r
+.nav .nav-divider {\r
+ height: 1px;\r
+ margin: 9px 0;\r
+ overflow: hidden;\r
+ background-color: #e5e5e5;\r
+}\r
+.nav > li > a > img {\r
+ max-width: none;\r
+}\r
+.nav-tabs {\r
+ border-bottom: 1px solid #dddddd;\r
+}\r
+.nav-tabs > li {\r
+ float: left;\r
+ margin-bottom: -1px;\r
+}\r
+.nav-tabs > li > a {\r
+ margin-right: 2px;\r
+ line-height: 1.428571429;\r
+ border: 1px solid transparent;\r
+ border-radius: 0px 0px 0 0;\r
+}\r
+.nav-tabs > li > a:hover {\r
+ border-color: #eeeeee #eeeeee #dddddd;\r
+}\r
+.nav-tabs > li.active > a,\r
+.nav-tabs > li.active > a:hover,\r
+.nav-tabs > li.active > a:focus {\r
+ color: #555555;\r
+ background-color: #f2f2f2;\r
+ border: 1px solid #dddddd;\r
+ border-bottom-color: transparent;\r
+ cursor: default;\r
+}\r
+.nav-tabs.nav-justified {\r
+ width: 100%;\r
+ border-bottom: 0;\r
+}\r
+.nav-tabs.nav-justified > li {\r
+ float: none;\r
+}\r
+.nav-tabs.nav-justified > li > a {\r
+ text-align: center;\r
+ margin-bottom: 5px;\r
+}\r
+.nav-tabs.nav-justified > .dropdown .dropdown-menu {\r
+ top: auto;\r
+ left: auto;\r
+}\r
+@media (min-width: 768px) {\r
+ .nav-tabs.nav-justified > li {\r
+ display: table-cell;\r
+ width: 1%;\r
+ }\r
+ .nav-tabs.nav-justified > li > a {\r
+ margin-bottom: 0;\r
+ }\r
+}\r
+.nav-tabs.nav-justified > li > a {\r
+ margin-right: 0;\r
+ border-radius: 0px;\r
+}\r
+.nav-tabs.nav-justified > .active > a,\r
+.nav-tabs.nav-justified > .active > a:hover,\r
+.nav-tabs.nav-justified > .active > a:focus {\r
+ border: 1px solid #dddddd;\r
+}\r
+@media (min-width: 768px) {\r
+ .nav-tabs.nav-justified > li > a {\r
+ border-bottom: 1px solid #dddddd;\r
+ border-radius: 0px 0px 0 0;\r
+ }\r
+ .nav-tabs.nav-justified > .active > a,\r
+ .nav-tabs.nav-justified > .active > a:hover,\r
+ .nav-tabs.nav-justified > .active > a:focus {\r
+ border-bottom-color: #f2f2f2;\r
+ }\r
+}\r
+.nav-pills > li {\r
+ float: left;\r
+}\r
+.nav-pills > li > a {\r
+ border-radius: 0px;\r
+}\r
+.nav-pills > li + li {\r
+ margin-left: 2px;\r
+}\r
+.nav-pills > li.active > a,\r
+.nav-pills > li.active > a:hover,\r
+.nav-pills > li.active > a:focus {\r
+ color: #ffffff;\r
+ background-color: #0d8921;\r
+}\r
+.nav-stacked > li {\r
+ float: none;\r
+}\r
+.nav-stacked > li + li {\r
+ margin-top: 2px;\r
+ margin-left: 0;\r
+}\r
+.nav-justified {\r
+ width: 100%;\r
+}\r
+.nav-justified > li {\r
+ float: none;\r
+}\r
+.nav-justified > li > a {\r
+ text-align: center;\r
+ margin-bottom: 5px;\r
+}\r
+.nav-justified > .dropdown .dropdown-menu {\r
+ top: auto;\r
+ left: auto;\r
+}\r
+@media (min-width: 768px) {\r
+ .nav-justified > li {\r
+ display: table-cell;\r
+ width: 1%;\r
+ }\r
+ .nav-justified > li > a {\r
+ margin-bottom: 0;\r
+ }\r
+}\r
+.nav-tabs-justified {\r
+ border-bottom: 0;\r
+}\r
+.nav-tabs-justified > li > a {\r
+ margin-right: 0;\r
+ border-radius: 0px;\r
+}\r
+.nav-tabs-justified > .active > a,\r
+.nav-tabs-justified > .active > a:hover,\r
+.nav-tabs-justified > .active > a:focus {\r
+ border: 1px solid #dddddd;\r
+}\r
+@media (min-width: 768px) {\r
+ .nav-tabs-justified > li > a {\r
+ border-bottom: 1px solid #dddddd;\r
+ border-radius: 0px 0px 0 0;\r
+ }\r
+ .nav-tabs-justified > .active > a,\r
+ .nav-tabs-justified > .active > a:hover,\r
+ .nav-tabs-justified > .active > a:focus {\r
+ border-bottom-color: #f2f2f2;\r
+ }\r
+}\r
+.tab-content > .tab-pane {\r
+ display: none;\r
+}\r
+.tab-content > .active {\r
+ display: block;\r
+}\r
+.nav-tabs .dropdown-menu {\r
+ margin-top: -1px;\r
+ border-top-right-radius: 0;\r
+ border-top-left-radius: 0;\r
+}\r
+.navbar {\r
+ position: relative;\r
+ min-height: 50px;\r
+ margin-bottom: 20px;\r
+ border: 1px solid transparent;\r
+}\r
+@media (min-width: 768px) {\r
+ .navbar {\r
+ border-radius: 0px;\r
+ }\r
+}\r
+@media (min-width: 768px) {\r
+ .navbar-header {\r
+ float: left;\r
+ }\r
+}\r
+.navbar-collapse {\r
+ max-height: 340px;\r
+ overflow-x: visible;\r
+ padding-right: 15px;\r
+ padding-left: 15px;\r
+ border-top: 1px solid transparent;\r
+ box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.1);\r
+ -webkit-overflow-scrolling: touch;\r
+}\r
+.navbar-collapse.in {\r
+ overflow-y: auto;\r
+}\r
+@media (min-width: 768px) {\r
+ .navbar-collapse {\r
+ width: auto;\r
+ border-top: 0;\r
+ box-shadow: none;\r
+ }\r
+ .navbar-collapse.collapse {\r
+ display: block !important;\r
+ height: auto !important;\r
+ padding-bottom: 0;\r
+ overflow: visible !important;\r
+ }\r
+ .navbar-collapse.in {\r
+ overflow-y: visible;\r
+ }\r
+ .navbar-fixed-top .navbar-collapse,\r
+ .navbar-static-top .navbar-collapse,\r
+ .navbar-fixed-bottom .navbar-collapse {\r
+ padding-left: 0;\r
+ padding-right: 0;\r
+ }\r
+}\r
+.container > .navbar-header,\r
+.container-fluid > .navbar-header,\r
+.container > .navbar-collapse,\r
+.container-fluid > .navbar-collapse {\r
+ margin-right: -15px;\r
+ margin-left: -15px;\r
+}\r
+@media (min-width: 768px) {\r
+ .container > .navbar-header,\r
+ .container-fluid > .navbar-header,\r
+ .container > .navbar-collapse,\r
+ .container-fluid > .navbar-collapse {\r
+ margin-right: 0;\r
+ margin-left: 0;\r
+ }\r
+}\r
+.navbar-static-top {\r
+ z-index: 1000;\r
+ border-width: 0 0 1px;\r
+}\r
+@media (min-width: 768px) {\r
+ .navbar-static-top {\r
+ border-radius: 0;\r
+ }\r
+}\r
+.navbar-fixed-top,\r
+.navbar-fixed-bottom {\r
+ position: fixed;\r
+ right: 0;\r
+ left: 0;\r
+ z-index: 1030;\r
+}\r
+@media (min-width: 768px) {\r
+ .navbar-fixed-top,\r
+ .navbar-fixed-bottom {\r
+ border-radius: 0;\r
+ }\r
+}\r
+.navbar-fixed-top {\r
+ top: 0;\r
+ border-width: 0 0 1px;\r
+}\r
+.navbar-fixed-bottom {\r
+ bottom: 0;\r
+ margin-bottom: 0;\r
+ border-width: 1px 0 0;\r
+}\r
+.navbar-brand {\r
+ float: left;\r
+ padding: 15px 15px;\r
+ font-size: 18px;\r
+ line-height: 20px;\r
+ height: 50px;\r
+}\r
+.navbar-brand:hover,\r
+.navbar-brand:focus {\r
+ text-decoration: none;\r
+}\r
+@media (min-width: 768px) {\r
+ .navbar > .container .navbar-brand,\r
+ .navbar > .container-fluid .navbar-brand {\r
+ margin-left: -15px;\r
+ }\r
+}\r
+.navbar-toggle {\r
+ position: relative;\r
+ float: right;\r
+ margin-right: 15px;\r
+ padding: 9px 10px;\r
+ margin-top: 8px;\r
+ margin-bottom: 8px;\r
+ background-color: transparent;\r
+ background-image: none;\r
+ border: 1px solid transparent;\r
+ border-radius: 0px;\r
+}\r
+.navbar-toggle:focus {\r
+ outline: none;\r
+}\r
+.navbar-toggle .icon-bar {\r
+ display: block;\r
+ width: 22px;\r
+ height: 2px;\r
+ border-radius: 1px;\r
+}\r
+.navbar-toggle .icon-bar + .icon-bar {\r
+ margin-top: 4px;\r
+}\r
+@media (min-width: 768px) {\r
+ .navbar-toggle {\r
+ display: none;\r
+ }\r
+}\r
+.navbar-nav {\r
+ margin: 7.5px -15px;\r
+}\r
+.navbar-nav > li > a {\r
+ padding-top: 10px;\r
+ padding-bottom: 10px;\r
+ line-height: 20px;\r
+}\r
+@media (max-width: 767px) {\r
+ .navbar-nav .open .dropdown-menu {\r
+ position: static;\r
+ float: none;\r
+ width: auto;\r
+ margin-top: 0;\r
+ background-color: transparent;\r
+ border: 0;\r
+ box-shadow: none;\r
+ }\r
+ .navbar-nav .open .dropdown-menu > li > a,\r
+ .navbar-nav .open .dropdown-menu .dropdown-header {\r
+ padding: 5px 15px 5px 25px;\r
+ }\r
+ .navbar-nav .open .dropdown-menu > li > a {\r
+ line-height: 20px;\r
+ }\r
+ .navbar-nav .open .dropdown-menu > li > a:hover,\r
+ .navbar-nav .open .dropdown-menu > li > a:focus {\r
+ background-image: none;\r
+ }\r
+}\r
+@media (min-width: 768px) {\r
+ .navbar-nav {\r
+ float: left;\r
+ margin: 0;\r
+ }\r
+ .navbar-nav > li {\r
+ float: left;\r
+ }\r
+ .navbar-nav > li > a {\r
+ padding-top: 15px;\r
+ padding-bottom: 15px;\r
+ }\r
+ .navbar-nav.navbar-right:last-child {\r
+ margin-right: -15px;\r
+ }\r
+}\r
+@media (min-width: 768px) {\r
+ .navbar-left {\r
+ float: left !important;\r
+ }\r
+ .navbar-right {\r
+ float: right !important;\r
+ }\r
+}\r
+.navbar-form {\r
+ margin-left: -15px;\r
+ margin-right: -15px;\r
+ padding: 10px 15px;\r
+ border-top: 1px solid transparent;\r
+ border-bottom: 1px solid transparent;\r
+ -webkit-box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.1), 0 1px 0 rgba(255, 255, 255, 0.1);\r
+ box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.1), 0 1px 0 rgba(255, 255, 255, 0.1);\r
+ margin-top: 8px;\r
+ margin-bottom: 8px;\r
+}\r
+@media (min-width: 768px) {\r
+ .navbar-form .form-group {\r
+ display: inline-block;\r
+ margin-bottom: 0;\r
+ vertical-align: middle;\r
+ }\r
+ .navbar-form .form-control {\r
+ display: inline-block;\r
+ width: auto;\r
+ vertical-align: middle;\r
+ }\r
+ .navbar-form .input-group > .form-control {\r
+ width: 100%;\r
+ }\r
+ .navbar-form .control-label {\r
+ margin-bottom: 0;\r
+ vertical-align: middle;\r
+ }\r
+ .navbar-form .radio,\r
+ .navbar-form .checkbox {\r
+ display: inline-block;\r
+ margin-top: 0;\r
+ margin-bottom: 0;\r
+ padding-left: 0;\r
+ vertical-align: middle;\r
+ }\r
+ .navbar-form .radio input[type="radio"],\r
+ .navbar-form .checkbox input[type="checkbox"] {\r
+ float: none;\r
+ margin-left: 0;\r
+ }\r
+ .navbar-form .has-feedback .form-control-feedback {\r
+ top: 0;\r
+ }\r
+}\r
+@media (max-width: 767px) {\r
+ .navbar-form .form-group {\r
+ margin-bottom: 5px;\r
+ }\r
+}\r
+@media (min-width: 768px) {\r
+ .navbar-form {\r
+ width: auto;\r
+ border: 0;\r
+ margin-left: 0;\r
+ margin-right: 0;\r
+ padding-top: 0;\r
+ padding-bottom: 0;\r
+ -webkit-box-shadow: none;\r
+ box-shadow: none;\r
+ }\r
+ .navbar-form.navbar-right:last-child {\r
+ margin-right: -15px;\r
+ }\r
+}\r
+.navbar-nav > li > .dropdown-menu {\r
+ margin-top: 0;\r
+ border-top-right-radius: 0;\r
+ border-top-left-radius: 0;\r
+}\r
+.navbar-fixed-bottom .navbar-nav > li > .dropdown-menu {\r
+ border-bottom-right-radius: 0;\r
+ border-bottom-left-radius: 0;\r
+}\r
+.navbar-btn {\r
+ margin-top: 8px;\r
+ margin-bottom: 8px;\r
+}\r
+.navbar-btn.btn-sm {\r
+ margin-top: 10px;\r
+ margin-bottom: 10px;\r
+}\r
+.navbar-btn.btn-xs {\r
+ margin-top: 14px;\r
+ margin-bottom: 14px;\r
+}\r
+.navbar-text {\r
+ margin-top: 15px;\r
+ margin-bottom: 15px;\r
+}\r
+@media (min-width: 768px) {\r
+ .navbar-text {\r
+ float: left;\r
+ margin-left: 15px;\r
+ margin-right: 15px;\r
+ }\r
+ .navbar-text.navbar-right:last-child {\r
+ margin-right: 0;\r
+ }\r
+}\r
+.navbar-default {\r
+ background-color: #0d8921;\r
+ border-color: none;\r
+}\r
+.navbar-default .navbar-brand {\r
+ color: #ffffff;\r
+}\r
+.navbar-default .navbar-brand:hover,\r
+.navbar-default .navbar-brand:focus {\r
+ color: #e6e6e6;\r
+ background-color: transparent;\r
+}\r
+.navbar-default .navbar-text {\r
+ color: #ffffff;\r
+}\r
+.navbar-default .navbar-nav > li > a {\r
+ color: #ffffff;\r
+}\r
+.navbar-default .navbar-nav > li > a:hover,\r
+.navbar-default .navbar-nav > li > a:focus {\r
+ color: #dddddd;\r
+ background-color: transparent;\r
+}\r
+.navbar-default .navbar-nav > .active > a,\r
+.navbar-default .navbar-nav > .active > a:hover,\r
+.navbar-default .navbar-nav > .active > a:focus {\r
+ color: #ffffff;\r
+ background-color: #0a6b1a;\r
+}\r
+.navbar-default .navbar-nav > .disabled > a,\r
+.navbar-default .navbar-nav > .disabled > a:hover,\r
+.navbar-default .navbar-nav > .disabled > a:focus {\r
+ color: #cccccc;\r
+ background-color: transparent;\r
+}\r
+.navbar-default .navbar-toggle {\r
+ border-color: #dddddd;\r
+}\r
+.navbar-default .navbar-toggle:hover,\r
+.navbar-default .navbar-toggle:focus {\r
+ background-color: #dddddd;\r
+}\r
+.navbar-default .navbar-toggle .icon-bar {\r
+ background-color: #ffffff;\r
+}\r
+.navbar-default .navbar-collapse,\r
+.navbar-default .navbar-form {\r
+ border-color: none;\r
+}\r
+.navbar-default .navbar-nav > .open > a,\r
+.navbar-default .navbar-nav > .open > a:hover,\r
+.navbar-default .navbar-nav > .open > a:focus {\r
+ background-color: #0a6b1a;\r
+ color: #ffffff;\r
+}\r
+@media (max-width: 767px) {\r
+ .navbar-default .navbar-nav .open .dropdown-menu > li > a {\r
+ color: #ffffff;\r
+ }\r
+ .navbar-default .navbar-nav .open .dropdown-menu > li > a:hover,\r
+ .navbar-default .navbar-nav .open .dropdown-menu > li > a:focus {\r
+ color: #dddddd;\r
+ background-color: transparent;\r
+ }\r
+ .navbar-default .navbar-nav .open .dropdown-menu > .active > a,\r
+ .navbar-default .navbar-nav .open .dropdown-menu > .active > a:hover,\r
+ .navbar-default .navbar-nav .open .dropdown-menu > .active > a:focus {\r
+ color: #ffffff;\r
+ background-color: #0a6b1a;\r
+ }\r
+ .navbar-default .navbar-nav .open .dropdown-menu > .disabled > a,\r
+ .navbar-default .navbar-nav .open .dropdown-menu > .disabled > a:hover,\r
+ .navbar-default .navbar-nav .open .dropdown-menu > .disabled > a:focus {\r
+ color: #cccccc;\r
+ background-color: transparent;\r
+ }\r
+}\r
+.navbar-default .navbar-link {\r
+ color: #ffffff;\r
+}\r
+.navbar-default .navbar-link:hover {\r
+ color: #dddddd;\r
+}\r
+.navbar-inverse {\r
+ background-color: #222222;\r
+ border-color: #080808;\r
+}\r
+.navbar-inverse .navbar-brand {\r
+ color: #999999;\r
+}\r
+.navbar-inverse .navbar-brand:hover,\r
+.navbar-inverse .navbar-brand:focus {\r
+ color: #ffffff;\r
+ background-color: transparent;\r
+}\r
+.navbar-inverse .navbar-text {\r
+ color: #999999;\r
+}\r
+.navbar-inverse .navbar-nav > li > a {\r
+ color: #999999;\r
+}\r
+.navbar-inverse .navbar-nav > li > a:hover,\r
+.navbar-inverse .navbar-nav > li > a:focus {\r
+ color: #ffffff;\r
+ background-color: transparent;\r
+}\r
+.navbar-inverse .navbar-nav > .active > a,\r
+.navbar-inverse .navbar-nav > .active > a:hover,\r
+.navbar-inverse .navbar-nav > .active > a:focus {\r
+ color: #ffffff;\r
+ background-color: #080808;\r
+}\r
+.navbar-inverse .navbar-nav > .disabled > a,\r
+.navbar-inverse .navbar-nav > .disabled > a:hover,\r
+.navbar-inverse .navbar-nav > .disabled > a:focus {\r
+ color: #444444;\r
+ background-color: transparent;\r
+}\r
+.navbar-inverse .navbar-toggle {\r
+ border-color: #333333;\r
+}\r
+.navbar-inverse .navbar-toggle:hover,\r
+.navbar-inverse .navbar-toggle:focus {\r
+ background-color: #333333;\r
+}\r
+.navbar-inverse .navbar-toggle .icon-bar {\r
+ background-color: #ffffff;\r
+}\r
+.navbar-inverse .navbar-collapse,\r
+.navbar-inverse .navbar-form {\r
+ border-color: #101010;\r
+}\r
+.navbar-inverse .navbar-nav > .open > a,\r
+.navbar-inverse .navbar-nav > .open > a:hover,\r
+.navbar-inverse .navbar-nav > .open > a:focus {\r
+ background-color: #080808;\r
+ color: #ffffff;\r
+}\r
+@media (max-width: 767px) {\r
+ .navbar-inverse .navbar-nav .open .dropdown-menu > .dropdown-header {\r
+ border-color: #080808;\r
+ }\r
+ .navbar-inverse .navbar-nav .open .dropdown-menu .divider {\r
+ background-color: #080808;\r
+ }\r
+ .navbar-inverse .navbar-nav .open .dropdown-menu > li > a {\r
+ color: #999999;\r
+ }\r
+ .navbar-inverse .navbar-nav .open .dropdown-menu > li > a:hover,\r
+ .navbar-inverse .navbar-nav .open .dropdown-menu > li > a:focus {\r
+ color: #ffffff;\r
+ background-color: transparent;\r
+ }\r
+ .navbar-inverse .navbar-nav .open .dropdown-menu > .active > a,\r
+ .navbar-inverse .navbar-nav .open .dropdown-menu > .active > a:hover,\r
+ .navbar-inverse .navbar-nav .open .dropdown-menu > .active > a:focus {\r
+ color: #ffffff;\r
+ background-color: #080808;\r
+ }\r
+ .navbar-inverse .navbar-nav .open .dropdown-menu > .disabled > a,\r
+ .navbar-inverse .navbar-nav .open .dropdown-menu > .disabled > a:hover,\r
+ .navbar-inverse .navbar-nav .open .dropdown-menu > .disabled > a:focus {\r
+ color: #444444;\r
+ background-color: transparent;\r
+ }\r
+}\r
+.navbar-inverse .navbar-link {\r
+ color: #999999;\r
+}\r
+.navbar-inverse .navbar-link:hover {\r
+ color: #ffffff;\r
+}\r
+.breadcrumb {\r
+ padding: 8px 15px;\r
+ margin-bottom: 20px;\r
+ list-style: none;\r
+ background-color: #f5f5f5;\r
+ border-radius: 0px;\r
+}\r
+.breadcrumb > li {\r
+ display: inline-block;\r
+}\r
+.breadcrumb > li + li:before {\r
+ content: "\00a0";\r
+ padding: 0 5px;\r
+ color: #cccccc;\r
+}\r
+.breadcrumb > .active {\r
+ color: #999999;\r
+}\r
+.pagination {\r
+ display: inline-block;\r
+ padding-left: 0;\r
+ margin: 20px 0;\r
+ border-radius: 0px;\r
+}\r
+.pagination > li {\r
+ display: inline;\r
+}\r
+.pagination > li > a,\r
+.pagination > li > span {\r
+ position: relative;\r
+ float: left;\r
+ padding: 6px 12px;\r
+ line-height: 1.428571429;\r
+ text-decoration: none;\r
+ color: #0d8921;\r
+ background-color: #ffffff;\r
+ border: 1px solid #dddddd;\r
+ margin-left: -1px;\r
+}\r
+.pagination > li:first-child > a,\r
+.pagination > li:first-child > span {\r
+ margin-left: 0;\r
+ border-bottom-left-radius: 0px;\r
+ border-top-left-radius: 0px;\r
+}\r
+.pagination > li:last-child > a,\r
+.pagination > li:last-child > span {\r
+ border-bottom-right-radius: 0px;\r
+ border-top-right-radius: 0px;\r
+}\r
+.pagination > li > a:hover,\r
+.pagination > li > span:hover,\r
+.pagination > li > a:focus,\r
+.pagination > li > span:focus {\r
+ color: #064310;\r
+ background-color: #eeeeee;\r
+ border-color: #dddddd;\r
+}\r
+.pagination > .active > a,\r
+.pagination > .active > span,\r
+.pagination > .active > a:hover,\r
+.pagination > .active > span:hover,\r
+.pagination > .active > a:focus,\r
+.pagination > .active > span:focus {\r
+ z-index: 2;\r
+ color: #ffffff;\r
+ background-color: #0d8921;\r
+ border-color: #0d8921;\r
+ cursor: default;\r
+}\r
+.pagination > .disabled > span,\r
+.pagination > .disabled > span:hover,\r
+.pagination > .disabled > span:focus,\r
+.pagination > .disabled > a,\r
+.pagination > .disabled > a:hover,\r
+.pagination > .disabled > a:focus {\r
+ color: #999999;\r
+ background-color: #ffffff;\r
+ border-color: #dddddd;\r
+ cursor: not-allowed;\r
+}\r
+.pagination-lg > li > a,\r
+.pagination-lg > li > span {\r
+ padding: 10px 16px;\r
+ font-size: 18px;\r
+}\r
+.pagination-lg > li:first-child > a,\r
+.pagination-lg > li:first-child > span {\r
+ border-bottom-left-radius: 0px;\r
+ border-top-left-radius: 0px;\r
+}\r
+.pagination-lg > li:last-child > a,\r
+.pagination-lg > li:last-child > span {\r
+ border-bottom-right-radius: 0px;\r
+ border-top-right-radius: 0px;\r
+}\r
+.pagination-sm > li > a,\r
+.pagination-sm > li > span {\r
+ padding: 5px 10px;\r
+ font-size: 12px;\r
+}\r
+.pagination-sm > li:first-child > a,\r
+.pagination-sm > li:first-child > span {\r
+ border-bottom-left-radius: 0px;\r
+ border-top-left-radius: 0px;\r
+}\r
+.pagination-sm > li:last-child > a,\r
+.pagination-sm > li:last-child > span {\r
+ border-bottom-right-radius: 0px;\r
+ border-top-right-radius: 0px;\r
+}\r
+.pager {\r
+ padding-left: 0;\r
+ margin: 20px 0;\r
+ list-style: none;\r
+ text-align: center;\r
+}\r
+.pager li {\r
+ display: inline;\r
+}\r
+.pager li > a,\r
+.pager li > span {\r
+ display: inline-block;\r
+ padding: 5px 14px;\r
+ background-color: #ffffff;\r
+ border: 1px solid #dddddd;\r
+ border-radius: 15px;\r
+}\r
+.pager li > a:hover,\r
+.pager li > a:focus {\r
+ text-decoration: none;\r
+ background-color: #eeeeee;\r
+}\r
+.pager .next > a,\r
+.pager .next > span {\r
+ float: right;\r
+}\r
+.pager .previous > a,\r
+.pager .previous > span {\r
+ float: left;\r
+}\r
+.pager .disabled > a,\r
+.pager .disabled > a:hover,\r
+.pager .disabled > a:focus,\r
+.pager .disabled > span {\r
+ color: #999999;\r
+ background-color: #ffffff;\r
+ cursor: not-allowed;\r
+}\r
+.label {\r
+ display: inline;\r
+ padding: .2em .6em .3em;\r
+ font-size: 75%;\r
+ font-weight: bold;\r
+ line-height: 1;\r
+ color: #ffffff;\r
+ text-align: center;\r
+ white-space: nowrap;\r
+ vertical-align: baseline;\r
+ border-radius: .25em;\r
+}\r
+.label[href]:hover,\r
+.label[href]:focus {\r
+ color: #ffffff;\r
+ text-decoration: none;\r
+ cursor: pointer;\r
+}\r
+.label:empty {\r
+ display: none;\r
+}\r
+.btn .label {\r
+ position: relative;\r
+ top: -1px;\r
+}\r
+.label-default {\r
+ background-color: #999999;\r
+}\r
+.label-default[href]:hover,\r
+.label-default[href]:focus {\r
+ background-color: #808080;\r
+}\r
+.label-primary {\r
+ background-color: #0d8921;\r
+}\r
+.label-primary[href]:hover,\r
+.label-primary[href]:focus {\r
+ background-color: #095a16;\r
+}\r
+.label-success {\r
+ background-color: #5cb85c;\r
+}\r
+.label-success[href]:hover,\r
+.label-success[href]:focus {\r
+ background-color: #449d44;\r
+}\r
+.label-info {\r
+ background-color: #5bc0de;\r
+}\r
+.label-info[href]:hover,\r
+.label-info[href]:focus {\r
+ background-color: #31b0d5;\r
+}\r
+.label-warning {\r
+ background-color: #f0ad4e;\r
+}\r
+.label-warning[href]:hover,\r
+.label-warning[href]:focus {\r
+ background-color: #ec971f;\r
+}\r
+.label-danger {\r
+ background-color: #d9534f;\r
+}\r
+.label-danger[href]:hover,\r
+.label-danger[href]:focus {\r
+ background-color: #c9302c;\r
+}\r
+.badge {\r
+ display: inline-block;\r
+ min-width: 10px;\r
+ padding: 3px 7px;\r
+ font-size: 12px;\r
+ font-weight: bold;\r
+ color: : #fff;\r
+ line-height: 1;\r
+ vertical-align: baseline;\r
+ white-space: nowrap;\r
+ text-align: center;\r
+ background-color: #999999;\r
+ border-radius: 10px;\r
+}\r
+.badge:empty {\r
+ display: none;\r
+}\r
+.btn .badge {\r
+ position: relative;\r
+ top: -1px;\r
+}\r
+.btn-xs .badge {\r
+ top: 0;\r
+ padding: 1px 5px;\r
+}\r
+a.badge:hover,\r
+a.badge:focus {\r
+ color: #ffffff;\r
+ text-decoration: none;\r
+ cursor: pointer;\r
+}\r
+a.list-group-item.active > .badge,\r
+.nav-pills > .active > a > .badge {\r
+ color: #0d8921;\r
+ background-color: #ffffff;\r
+}\r
+.nav-pills > li > a > .badge {\r
+ margin-left: 3px;\r
+}\r
+.jumbotron {\r
+ padding: 30px;\r
+ margin-bottom: 30px;\r
+ color: inherit;\r
+ background-color: #ffffff;\r
+}\r
+.jumbotron h1,\r
+.jumbotron .h1 {\r
+ color: inherit;\r
+}\r
+.jumbotron p {\r
+ margin-bottom: 15px;\r
+ font-size: 21px;\r
+ font-weight: 200;\r
+}\r
+.container .jumbotron {\r
+ border-radius: 0px;\r
+}\r
+.jumbotron .container {\r
+ max-width: 100%;\r
+}\r
+@media screen and (min-width: 768px) {\r
+ .jumbotron {\r
+ padding-top: 48px;\r
+ padding-bottom: 48px;\r
+ }\r
+ .container .jumbotron {\r
+ padding-left: 60px;\r
+ padding-right: 60px;\r
+ }\r
+ .jumbotron h1,\r
+ .jumbotron .h1 {\r
+ font-size: 63px;\r
+ }\r
+}\r
+.thumbnail {\r
+ display: block;\r
+ padding: 4px;\r
+ margin-bottom: 20px;\r
+ line-height: 1.428571429;\r
+ background-color: #f2f2f2;\r
+ border: 1px solid #dddddd;\r
+ border-radius: 0px;\r
+ -webkit-transition: all 0.2s ease-in-out;\r
+ transition: all 0.2s ease-in-out;\r
+}\r
+.thumbnail > img,\r
+.thumbnail a > img {\r
+ margin-left: auto;\r
+ margin-right: auto;\r
+}\r
+a.thumbnail:hover,\r
+a.thumbnail:focus,\r
+a.thumbnail.active {\r
+ border-color: #0d8921;\r
+}\r
+.thumbnail .caption {\r
+ padding: 9px;\r
+ color: #333333;\r
+}\r
+.alert {\r
+ padding: 15px;\r
+ margin-bottom: 20px;\r
+ border: 1px solid transparent;\r
+ border-radius: 0px;\r
+}\r
+.alert h4 {\r
+ margin-top: 0;\r
+ color: inherit;\r
+}\r
+.alert .alert-link {\r
+ font-weight: bold;\r
+}\r
+.alert > p,\r
+.alert > ul {\r
+ margin-bottom: 0;\r
+}\r
+.alert > p + p {\r
+ margin-top: 5px;\r
+}\r
+.alert-dismissable {\r
+ padding-right: 35px;\r
+}\r
+.alert-dismissable .close {\r
+ position: relative;\r
+ top: -2px;\r
+ right: -21px;\r
+ color: inherit;\r
+}\r
+.alert-success {\r
+ background-color: #dff0d8;\r
+ border-color: #d6e9c6;\r
+ color: #5cb85c;\r
+}\r
+.alert-success hr {\r
+ border-top-color: #c9e2b3;\r
+}\r
+.alert-success .alert-link {\r
+ color: #449d44;\r
+}\r
+.alert-info {\r
+ background-color: #d9edf7;\r
+ border-color: #bce8f1;\r
+ color: #5bc0de;\r
+}\r
+.alert-info hr {\r
+ border-top-color: #a6e1ec;\r
+}\r
+.alert-info .alert-link {\r
+ color: #31b0d5;\r
+}\r
+.alert-warning {\r
+ background-color: #fcf8e3;\r
+ border-color: #fbeed5;\r
+ color: #f0ad4e;\r
+}\r
+.alert-warning hr {\r
+ border-top-color: #f8e5be;\r
+}\r
+.alert-warning .alert-link {\r
+ color: #ec971f;\r
+}\r
+.alert-danger {\r
+ background-color: #f2dede;\r
+ border-color: #eed3d7;\r
+ color: #d9534f;\r
+}\r
+.alert-danger hr {\r
+ border-top-color: #e6c1c7;\r
+}\r
+.alert-danger .alert-link {\r
+ color: #c9302c;\r
+}\r
+@-webkit-keyframes progress-bar-stripes {\r
+ from {\r
+ background-position: 40px 0;\r
+ }\r
+ to {\r
+ background-position: 0 0;\r
+ }\r
+}\r
+@keyframes progress-bar-stripes {\r
+ from {\r
+ background-position: 40px 0;\r
+ }\r
+ to {\r
+ background-position: 0 0;\r
+ }\r
+}\r
+.progress {\r
+ overflow: hidden;\r
+ height: 20px;\r
+ margin-bottom: 20px;\r
+ background-color: #f5f5f5;\r
+ border-radius: 0px;\r
+ -webkit-box-shadow: inset 0 1px 2px rgba(0, 0, 0, 0.1);\r
+ box-shadow: inset 0 1px 2px rgba(0, 0, 0, 0.1);\r
+}\r
+.progress-bar {\r
+ float: left;\r
+ width: 0%;\r
+ height: 100%;\r
+ font-size: 12px;\r
+ line-height: 20px;\r
+ color: #ffffff;\r
+ text-align: center;\r
+ background-color: #0d8921;\r
+ -webkit-box-shadow: inset 0 -1px 0 rgba(0, 0, 0, 0.15);\r
+ box-shadow: inset 0 -1px 0 rgba(0, 0, 0, 0.15);\r
+ -webkit-transition: width 0.6s ease;\r
+ transition: width 0.6s ease;\r
+}\r
+.progress-striped .progress-bar {\r
+ background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\r
+ background-image: linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\r
+ background-size: 40px 40px;\r
+}\r
+.progress.active .progress-bar {\r
+ -webkit-animation: progress-bar-stripes 2s linear infinite;\r
+ animation: progress-bar-stripes 2s linear infinite;\r
+}\r
+.progress-bar-success {\r
+ background-color: #5cb85c;\r
+}\r
+.progress-striped .progress-bar-success {\r
+ background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\r
+ background-image: linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\r
+}\r
+.progress-bar-info {\r
+ background-color: #5bc0de;\r
+}\r
+.progress-striped .progress-bar-info {\r
+ background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\r
+ background-image: linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\r
+}\r
+.progress-bar-warning {\r
+ background-color: #f0ad4e;\r
+}\r
+.progress-striped .progress-bar-warning {\r
+ background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\r
+ background-image: linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\r
+}\r
+.progress-bar-danger {\r
+ background-color: #d9534f;\r
+}\r
+.progress-striped .progress-bar-danger {\r
+ background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\r
+ background-image: linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);\r
+}\r
+.media,\r
+.media-body {\r
+ overflow: hidden;\r
+ zoom: 1;\r
+}\r
+.media,\r
+.media .media {\r
+ margin-top: 15px;\r
+}\r
+.media:first-child {\r
+ margin-top: 0;\r
+}\r
+.media-object {\r
+ display: block;\r
+}\r
+.media-heading {\r
+ margin: 0 0 5px;\r
+}\r
+.media > .pull-left {\r
+ margin-right: 10px;\r
+}\r
+.media > .pull-right {\r
+ margin-left: 10px;\r
+}\r
+.media-list {\r
+ padding-left: 0;\r
+ list-style: none;\r
+}\r
+.list-group {\r
+ margin-bottom: 20px;\r
+ padding-left: 0;\r
+}\r
+.list-group-item {\r
+ position: relative;\r
+ display: block;\r
+ padding: 10px 15px;\r
+ margin-bottom: -1px;\r
+ background-color: #ffffff;\r
+ border: 1px solid #dddddd;\r
+}\r
+.list-group-item:first-child {\r
+ border-top-right-radius: 0px;\r
+ border-top-left-radius: 0px;\r
+}\r
+.list-group-item:last-child {\r
+ margin-bottom: 0;\r
+ border-bottom-right-radius: 0px;\r
+ border-bottom-left-radius: 0px;\r
+}\r
+.list-group-item > .badge {\r
+ float: right;\r
+}\r
+.list-group-item > .badge + .badge {\r
+ margin-right: 5px;\r
+}\r
+a.list-group-item {\r
+ color: #555555;\r
+}\r
+a.list-group-item .list-group-item-heading {\r
+ color: #333333;\r
+}\r
+a.list-group-item:hover,\r
+a.list-group-item:focus {\r
+ text-decoration: none;\r
+ background-color: #f5f5f5;\r
+}\r
+a.list-group-item.active,\r
+a.list-group-item.active:hover,\r
+a.list-group-item.active:focus {\r
+ z-index: 2;\r
+ color: #ffffff;\r
+ background-color: #0d8921;\r
+ border-color: #0d8921;\r
+}\r
+a.list-group-item.active .list-group-item-heading,\r
+a.list-group-item.active:hover .list-group-item-heading,\r
+a.list-group-item.active:focus .list-group-item-heading {\r
+ color: inherit;\r
+}\r
+a.list-group-item.active .list-group-item-text,\r
+a.list-group-item.active:hover .list-group-item-text,\r
+a.list-group-item.active:focus .list-group-item-text {\r
+ color: #cccccc;\r
+}\r
+.list-group-item-success {\r
+ color: #5cb85c;\r
+ background-color: #dff0d8;\r
+}\r
+a.list-group-item-success {\r
+ color: #5cb85c;\r
+}\r
+a.list-group-item-success .list-group-item-heading {\r
+ color: inherit;\r
+}\r
+a.list-group-item-success:hover,\r
+a.list-group-item-success:focus {\r
+ color: #5cb85c;\r
+ background-color: #d0e9c6;\r
+}\r
+a.list-group-item-success.active,\r
+a.list-group-item-success.active:hover,\r
+a.list-group-item-success.active:focus {\r
+ color: #fff;\r
+ background-color: #5cb85c;\r
+ border-color: #5cb85c;\r
+}\r
+.list-group-item-info {\r
+ color: #5bc0de;\r
+ background-color: #d9edf7;\r
+}\r
+a.list-group-item-info {\r
+ color: #5bc0de;\r
+}\r
+a.list-group-item-info .list-group-item-heading {\r
+ color: inherit;\r
+}\r
+a.list-group-item-info:hover,\r
+a.list-group-item-info:focus {\r
+ color: #5bc0de;\r
+ background-color: #c4e3f3;\r
+}\r
+a.list-group-item-info.active,\r
+a.list-group-item-info.active:hover,\r
+a.list-group-item-info.active:focus {\r
+ color: #fff;\r
+ background-color: #5bc0de;\r
+ border-color: #5bc0de;\r
+}\r
+.list-group-item-warning {\r
+ color: #f0ad4e;\r
+ background-color: #fcf8e3;\r
+}\r
+a.list-group-item-warning {\r
+ color: #f0ad4e;\r
+}\r
+a.list-group-item-warning .list-group-item-heading {\r
+ color: inherit;\r
+}\r
+a.list-group-item-warning:hover,\r
+a.list-group-item-warning:focus {\r
+ color: #f0ad4e;\r
+ background-color: #faf2cc;\r
+}\r
+a.list-group-item-warning.active,\r
+a.list-group-item-warning.active:hover,\r
+a.list-group-item-warning.active:focus {\r
+ color: #fff;\r
+ background-color: #f0ad4e;\r
+ border-color: #f0ad4e;\r
+}\r
+.list-group-item-danger {\r
+ color: #d9534f;\r
+ background-color: #f2dede;\r
+}\r
+a.list-group-item-danger {\r
+ color: #d9534f;\r
+}\r
+a.list-group-item-danger .list-group-item-heading {\r
+ color: inherit;\r
+}\r
+a.list-group-item-danger:hover,\r
+a.list-group-item-danger:focus {\r
+ color: #d9534f;\r
+ background-color: #ebcccc;\r
+}\r
+a.list-group-item-danger.active,\r
+a.list-group-item-danger.active:hover,\r
+a.list-group-item-danger.active:focus {\r
+ color: #fff;\r
+ background-color: #d9534f;\r
+ border-color: #d9534f;\r
+}\r
+.list-group-item-heading {\r
+ margin-top: 0;\r
+ margin-bottom: 5px;\r
+}\r
+.list-group-item-text {\r
+ margin-bottom: 0;\r
+ line-height: 1.3;\r
+}\r
+.panel {\r
+ margin-bottom: 20px;\r
+ background-color: #ffffff;\r
+ border: 1px solid transparent;\r
+ border-radius: 0px;\r
+ -webkit-box-shadow: 0 1px 1px rgba(0, 0, 0, 0.05);\r
+ box-shadow: 0 1px 1px rgba(0, 0, 0, 0.05);\r
+}\r
+.panel-body {\r
+ padding: 15px;\r
+}\r
+.panel-heading {\r
+ padding: 10px 15px;\r
+ border-bottom: 1px solid transparent;\r
+ border-top-right-radius: -1px;\r
+ border-top-left-radius: -1px;\r
+}\r
+.panel-heading > .dropdown .dropdown-toggle {\r
+ color: inherit;\r
+}\r
+.panel-title {\r
+ margin-top: 0;\r
+ margin-bottom: 0;\r
+ font-size: 16px;\r
+ color: inherit;\r
+}\r
+.panel-title > a {\r
+ color: inherit;\r
+}\r
+.panel-footer {\r
+ padding: 10px 15px;\r
+ background-color: #f5f5f5;\r
+ border-top: 1px solid #dddddd;\r
+ border-bottom-right-radius: -1px;\r
+ border-bottom-left-radius: -1px;\r
+}\r
+.panel > .list-group {\r
+ margin-bottom: 0;\r
+}\r
+.panel > .list-group .list-group-item {\r
+ border-width: 1px 0;\r
+ border-radius: 0;\r
+}\r
+.panel > .list-group .list-group-item:first-child {\r
+ border-top: 0;\r
+}\r
+.panel > .list-group .list-group-item:last-child {\r
+ border-bottom: 0;\r
+}\r
+.panel > .list-group:first-child .list-group-item:first-child {\r
+ border-top-right-radius: -1px;\r
+ border-top-left-radius: -1px;\r
+}\r
+.panel > .list-group:last-child .list-group-item:last-child {\r
+ border-bottom-right-radius: -1px;\r
+ border-bottom-left-radius: -1px;\r
+}\r
+.panel-heading + .list-group .list-group-item:first-child {\r
+ border-top-width: 0;\r
+}\r
+.panel > .table,\r
+.panel > .table-responsive > .table {\r
+ margin-bottom: 0;\r
+}\r
+.panel > .table:first-child > thead:first-child > tr:first-child td:first-child,\r
+.panel > .table-responsive:first-child > .table:first-child > thead:first-child > tr:first-child td:first-child,\r
+.panel > .table:first-child > tbody:first-child > tr:first-child td:first-child,\r
+.panel > .table-responsive:first-child > .table:first-child > tbody:first-child > tr:first-child td:first-child,\r
+.panel > .table:first-child > thead:first-child > tr:first-child th:first-child,\r
+.panel > .table-responsive:first-child > .table:first-child > thead:first-child > tr:first-child th:first-child,\r
+.panel > .table:first-child > tbody:first-child > tr:first-child th:first-child,\r
+.panel > .table-responsive:first-child > .table:first-child > tbody:first-child > tr:first-child th:first-child {\r
+ border-top-left-radius: -1px;\r
+}\r
+.panel > .table:first-child > thead:first-child > tr:first-child td:last-child,\r
+.panel > .table-responsive:first-child > .table:first-child > thead:first-child > tr:first-child td:last-child,\r
+.panel > .table:first-child > tbody:first-child > tr:first-child td:last-child,\r
+.panel > .table-responsive:first-child > .table:first-child > tbody:first-child > tr:first-child td:last-child,\r
+.panel > .table:first-child > thead:first-child > tr:first-child th:last-child,\r
+.panel > .table-responsive:first-child > .table:first-child > thead:first-child > tr:first-child th:last-child,\r
+.panel > .table:first-child > tbody:first-child > tr:first-child th:last-child,\r
+.panel > .table-responsive:first-child > .table:first-child > tbody:first-child > tr:first-child th:last-child {\r
+ border-top-right-radius: -1px;\r
+}\r
+.panel > .table:last-child > tbody:last-child > tr:last-child td:first-child,\r
+.panel > .table-responsive:last-child > .table:last-child > tbody:last-child > tr:last-child td:first-child,\r
+.panel > .table:last-child > tfoot:last-child > tr:last-child td:first-child,\r
+.panel > .table-responsive:last-child > .table:last-child > tfoot:last-child > tr:last-child td:first-child,\r
+.panel > .table:last-child > tbody:last-child > tr:last-child th:first-child,\r
+.panel > .table-responsive:last-child > .table:last-child > tbody:last-child > tr:last-child th:first-child,\r
+.panel > .table:last-child > tfoot:last-child > tr:last-child th:first-child,\r
+.panel > .table-responsive:last-child > .table:last-child > tfoot:last-child > tr:last-child th:first-child {\r
+ border-bottom-left-radius: -1px;\r
+}\r
+.panel > .table:last-child > tbody:last-child > tr:last-child td:last-child,\r
+.panel > .table-responsive:last-child > .table:last-child > tbody:last-child > tr:last-child td:last-child,\r
+.panel > .table:last-child > tfoot:last-child > tr:last-child td:last-child,\r
+.panel > .table-responsive:last-child > .table:last-child > tfoot:last-child > tr:last-child td:last-child,\r
+.panel > .table:last-child > tbody:last-child > tr:last-child th:last-child,\r
+.panel > .table-responsive:last-child > .table:last-child > tbody:last-child > tr:last-child th:last-child,\r
+.panel > .table:last-child > tfoot:last-child > tr:last-child th:last-child,\r
+.panel > .table-responsive:last-child > .table:last-child > tfoot:last-child > tr:last-child th:last-child {\r
+ border-bottom-right-radius: -1px;\r
+}\r
+.panel > .panel-body + .table,\r
+.panel > .panel-body + .table-responsive {\r
+ border-top: 1px solid #dddddd;\r
+}\r
+.panel > .table > tbody:first-child > tr:first-child th,\r
+.panel > .table > tbody:first-child > tr:first-child td {\r
+ border-top: 0;\r
+}\r
+.panel > .table-bordered,\r
+.panel > .table-responsive > .table-bordered {\r
+ border: 0;\r
+}\r
+.panel > .table-bordered > thead > tr > th:first-child,\r
+.panel > .table-responsive > .table-bordered > thead > tr > th:first-child,\r
+.panel > .table-bordered > tbody > tr > th:first-child,\r
+.panel > .table-responsive > .table-bordered > tbody > tr > th:first-child,\r
+.panel > .table-bordered > tfoot > tr > th:first-child,\r
+.panel > .table-responsive > .table-bordered > tfoot > tr > th:first-child,\r
+.panel > .table-bordered > thead > tr > td:first-child,\r
+.panel > .table-responsive > .table-bordered > thead > tr > td:first-child,\r
+.panel > .table-bordered > tbody > tr > td:first-child,\r
+.panel > .table-responsive > .table-bordered > tbody > tr > td:first-child,\r
+.panel > .table-bordered > tfoot > tr > td:first-child,\r
+.panel > .table-responsive > .table-bordered > tfoot > tr > td:first-child {\r
+ border-left: 0;\r
+}\r
+.panel > .table-bordered > thead > tr > th:last-child,\r
+.panel > .table-responsive > .table-bordered > thead > tr > th:last-child,\r
+.panel > .table-bordered > tbody > tr > th:last-child,\r
+.panel > .table-responsive > .table-bordered > tbody > tr > th:last-child,\r
+.panel > .table-bordered > tfoot > tr > th:last-child,\r
+.panel > .table-responsive > .table-bordered > tfoot > tr > th:last-child,\r
+.panel > .table-bordered > thead > tr > td:last-child,\r
+.panel > .table-responsive > .table-bordered > thead > tr > td:last-child,\r
+.panel > .table-bordered > tbody > tr > td:last-child,\r
+.panel > .table-responsive > .table-bordered > tbody > tr > td:last-child,\r
+.panel > .table-bordered > tfoot > tr > td:last-child,\r
+.panel > .table-responsive > .table-bordered > tfoot > tr > td:last-child {\r
+ border-right: 0;\r
+}\r
+.panel > .table-bordered > thead > tr:first-child > td,\r
+.panel > .table-responsive > .table-bordered > thead > tr:first-child > td,\r
+.panel > .table-bordered > tbody > tr:first-child > td,\r
+.panel > .table-responsive > .table-bordered > tbody > tr:first-child > td,\r
+.panel > .table-bordered > thead > tr:first-child > th,\r
+.panel > .table-responsive > .table-bordered > thead > tr:first-child > th,\r
+.panel > .table-bordered > tbody > tr:first-child > th,\r
+.panel > .table-responsive > .table-bordered > tbody > tr:first-child > th {\r
+ border-bottom: 0;\r
+}\r
+.panel > .table-bordered > tbody > tr:last-child > td,\r
+.panel > .table-responsive > .table-bordered > tbody > tr:last-child > td,\r
+.panel > .table-bordered > tfoot > tr:last-child > td,\r
+.panel > .table-responsive > .table-bordered > tfoot > tr:last-child > td,\r
+.panel > .table-bordered > tbody > tr:last-child > th,\r
+.panel > .table-responsive > .table-bordered > tbody > tr:last-child > th,\r
+.panel > .table-bordered > tfoot > tr:last-child > th,\r
+.panel > .table-responsive > .table-bordered > tfoot > tr:last-child > th {\r
+ border-bottom: 0;\r
+}\r
+.panel > .table-responsive {\r
+ border: 0;\r
+ margin-bottom: 0;\r
+}\r
+.panel-group {\r
+ margin-bottom: 20px;\r
+}\r
+.panel-group .panel {\r
+ margin-bottom: 0;\r
+ border-radius: 0px;\r
+ overflow: hidden;\r
+}\r
+.panel-group .panel + .panel {\r
+ margin-top: 5px;\r
+}\r
+.panel-group .panel-heading {\r
+ border-bottom: 0;\r
+}\r
+.panel-group .panel-heading + .panel-collapse .panel-body {\r
+ border-top: 1px solid #dddddd;\r
+}\r
+.panel-group .panel-footer {\r
+ border-top: 0;\r
+}\r
+.panel-group .panel-footer + .panel-collapse .panel-body {\r
+ border-bottom: 1px solid #dddddd;\r
+}\r
+.panel-default {\r
+ border-color: #dddddd;\r
+}\r
+.panel-default > .panel-heading {\r
+ color: #333333;\r
+ background-color: #f5f5f5;\r
+ border-color: #dddddd;\r
+}\r
+.panel-default > .panel-heading + .panel-collapse .panel-body {\r
+ border-top-color: #dddddd;\r
+}\r
+.panel-default > .panel-footer + .panel-collapse .panel-body {\r
+ border-bottom-color: #dddddd;\r
+}\r
+.panel-primary {\r
+ border-color: #0d8921;\r
+}\r
+.panel-primary > .panel-heading {\r
+ color: #ffffff;\r
+ background-color: #0d8921;\r
+ border-color: #0d8921;\r
+}\r
+.panel-primary > .panel-heading + .panel-collapse .panel-body {\r
+ border-top-color: #0d8921;\r
+}\r
+.panel-primary > .panel-footer + .panel-collapse .panel-body {\r
+ border-bottom-color: #0d8921;\r
+}\r
+.panel-success {\r
+ border-color: #d6e9c6;\r
+}\r
+.panel-success > .panel-heading {\r
+ color: #5cb85c;\r
+ background-color: #dff0d8;\r
+ border-color: #d6e9c6;\r
+}\r
+.panel-success > .panel-heading + .panel-collapse .panel-body {\r
+ border-top-color: #d6e9c6;\r
+}\r
+.panel-success > .panel-footer + .panel-collapse .panel-body {\r
+ border-bottom-color: #d6e9c6;\r
+}\r
+.panel-info {\r
+ border-color: #bce8f1;\r
+}\r
+.panel-info > .panel-heading {\r
+ color: #5bc0de;\r
+ background-color: #d9edf7;\r
+ border-color: #bce8f1;\r
+}\r
+.panel-info > .panel-heading + .panel-collapse .panel-body {\r
+ border-top-color: #bce8f1;\r
+}\r
+.panel-info > .panel-footer + .panel-collapse .panel-body {\r
+ border-bottom-color: #bce8f1;\r
+}\r
+.panel-warning {\r
+ border-color: #fbeed5;\r
+}\r
+.panel-warning > .panel-heading {\r
+ color: #f0ad4e;\r
+ background-color: #fcf8e3;\r
+ border-color: #fbeed5;\r
+}\r
+.panel-warning > .panel-heading + .panel-collapse .panel-body {\r
+ border-top-color: #fbeed5;\r
+}\r
+.panel-warning > .panel-footer + .panel-collapse .panel-body {\r
+ border-bottom-color: #fbeed5;\r
+}\r
+.panel-danger {\r
+ border-color: #eed3d7;\r
+}\r
+.panel-danger > .panel-heading {\r
+ color: #d9534f;\r
+ background-color: #f2dede;\r
+ border-color: #eed3d7;\r
+}\r
+.panel-danger > .panel-heading + .panel-collapse .panel-body {\r
+ border-top-color: #eed3d7;\r
+}\r
+.panel-danger > .panel-footer + .panel-collapse .panel-body {\r
+ border-bottom-color: #eed3d7;\r
+}\r
+.well {\r
+ min-height: 20px;\r
+ padding: 19px;\r
+ margin-bottom: 20px;\r
+ background-color: #f5f5f5;\r
+ border: 1px solid #e3e3e3;\r
+ border-radius: 0px;\r
+ -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.05);\r
+ box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.05);\r
+}\r
+.well blockquote {\r
+ border-color: #ddd;\r
+ border-color: rgba(0, 0, 0, 0.15);\r
+}\r
+.well-lg {\r
+ padding: 24px;\r
+ border-radius: 0px;\r
+}\r
+.well-sm {\r
+ padding: 9px;\r
+ border-radius: 0px;\r
+}\r
+.close {\r
+ float: right;\r
+ font-size: 21px;\r
+ font-weight: bold;\r
+ line-height: 1;\r
+ color: #000000;\r
+ text-shadow: 0 1px 0 #ffffff;\r
+ opacity: 0.2;\r
+ filter: alpha(opacity=20);\r
+}\r
+.close:hover,\r
+.close:focus {\r
+ color: #000000;\r
+ text-decoration: none;\r
+ cursor: pointer;\r
+ opacity: 0.5;\r
+ filter: alpha(opacity=50);\r
+}\r
+button.close {\r
+ padding: 0;\r
+ cursor: pointer;\r
+ background: transparent;\r
+ border: 0;\r
+ -webkit-appearance: none;\r
+}\r
+.modal-open {\r
+ overflow: hidden;\r
+}\r
+.modal {\r
+ display: none;\r
+ overflow: auto;\r
+ overflow-y: scroll;\r
+ position: fixed;\r
+ top: 0;\r
+ right: 0;\r
+ bottom: 0;\r
+ left: 0;\r
+ z-index: 1050;\r
+ -webkit-overflow-scrolling: touch;\r
+ outline: 0;\r
+}\r
+.modal.fade .modal-dialog {\r
+ -webkit-transform: translate(0, -25%);\r
+ -ms-transform: translate(0, -25%);\r
+ transform: translate(0, -25%);\r
+ -webkit-transition: -webkit-transform 0.3s ease-out;\r
+ -moz-transition: -moz-transform 0.3s ease-out;\r
+ -o-transition: -o-transform 0.3s ease-out;\r
+ transition: transform 0.3s ease-out;\r
+}\r
+.modal.in .modal-dialog {\r
+ -webkit-transform: translate(0, 0);\r
+ -ms-transform: translate(0, 0);\r
+ transform: translate(0, 0);\r
+}\r
+.modal-dialog {\r
+ position: relative;\r
+ width: auto;\r
+ margin: 10px;\r
+}\r
+.modal-content {\r
+ position: relative;\r
+ background-color: #ffffff;\r
+ border: 1px solid #999999;\r
+ border: 1px solid rgba(0, 0, 0, 0.2);\r
+ border-radius: 0px;\r
+ -webkit-box-shadow: 0 3px 9px rgba(0, 0, 0, 0.5);\r
+ box-shadow: 0 3px 9px rgba(0, 0, 0, 0.5);\r
+ background-clip: padding-box;\r
+ outline: none;\r
+}\r
+.modal-backdrop {\r
+ position: fixed;\r
+ top: 0;\r
+ right: 0;\r
+ bottom: 0;\r
+ left: 0;\r
+ z-index: 1040;\r
+ background-color: #000000;\r
+}\r
+.modal-backdrop.fade {\r
+ opacity: 0;\r
+ filter: alpha(opacity=0);\r
+}\r
+.modal-backdrop.in {\r
+ opacity: 0.5;\r
+ filter: alpha(opacity=50);\r
+}\r
+.modal-header {\r
+ padding: 15px;\r
+ border-bottom: 1px solid #e5e5e5;\r
+ min-height: 16.428571429px;\r
+}\r
+.modal-header .close {\r
+ margin-top: -2px;\r
+}\r
+.modal-title {\r
+ margin: 0;\r
+ line-height: 1.428571429;\r
+}\r
+.modal-body {\r
+ position: relative;\r
+ padding: 20px;\r
+}\r
+.modal-footer {\r
+ margin-top: 15px;\r
+ padding: 19px 20px 20px;\r
+ text-align: right;\r
+ border-top: 1px solid #e5e5e5;\r
+}\r
+.modal-footer .btn + .btn {\r
+ margin-left: 5px;\r
+ margin-bottom: 0;\r
+}\r
+.modal-footer .btn-group .btn + .btn {\r
+ margin-left: -1px;\r
+}\r
+.modal-footer .btn-block + .btn-block {\r
+ margin-left: 0;\r
+}\r
+@media (min-width: 768px) {\r
+ .modal-dialog {\r
+ width: 600px;\r
+ margin: 30px auto;\r
+ }\r
+ .modal-content {\r
+ -webkit-box-shadow: 0 5px 15px rgba(0, 0, 0, 0.5);\r
+ box-shadow: 0 5px 15px rgba(0, 0, 0, 0.5);\r
+ }\r
+ .modal-sm {\r
+ width: 300px;\r
+ }\r
+}\r
+@media (min-width: 992px) {\r
+ .modal-lg {\r
+ width: 900px;\r
+ }\r
+}\r
+.tooltip {\r
+ position: absolute;\r
+ z-index: 1030;\r
+ display: block;\r
+ visibility: visible;\r
+ font-size: 12px;\r
+ line-height: 1.4;\r
+ opacity: 0;\r
+ filter: alpha(opacity=0);\r
+}\r
+.tooltip.in {\r
+ opacity: 0.9;\r
+ filter: alpha(opacity=90);\r
+}\r
+.tooltip.top {\r
+ margin-top: -3px;\r
+ padding: 5px 0;\r
+}\r
+.tooltip.right {\r
+ margin-left: 3px;\r
+ padding: 0 5px;\r
+}\r
+.tooltip.bottom {\r
+ margin-top: 3px;\r
+ padding: 5px 0;\r
+}\r
+.tooltip.left {\r
+ margin-left: -3px;\r
+ padding: 0 5px;\r
+}\r
+.tooltip-inner {\r
+ max-width: 200px;\r
+ padding: 3px 8px;\r
+ color: #ffffff;\r
+ text-align: center;\r
+ text-decoration: none;\r
+ background-color: #000000;\r
+ border-radius: 0px;\r
+}\r
+.tooltip-arrow {\r
+ position: absolute;\r
+ width: 0;\r
+ height: 0;\r
+ border-color: transparent;\r
+ border-style: solid;\r
+}\r
+.tooltip.top .tooltip-arrow {\r
+ bottom: 0;\r
+ left: 50%;\r
+ margin-left: -5px;\r
+ border-width: 5px 5px 0;\r
+ border-top-color: #000000;\r
+}\r
+.tooltip.top-left .tooltip-arrow {\r
+ bottom: 0;\r
+ left: 5px;\r
+ border-width: 5px 5px 0;\r
+ border-top-color: #000000;\r
+}\r
+.tooltip.top-right .tooltip-arrow {\r
+ bottom: 0;\r
+ right: 5px;\r
+ border-width: 5px 5px 0;\r
+ border-top-color: #000000;\r
+}\r
+.tooltip.right .tooltip-arrow {\r
+ top: 50%;\r
+ left: 0;\r
+ margin-top: -5px;\r
+ border-width: 5px 5px 5px 0;\r
+ border-right-color: #000000;\r
+}\r
+.tooltip.left .tooltip-arrow {\r
+ top: 50%;\r
+ right: 0;\r
+ margin-top: -5px;\r
+ border-width: 5px 0 5px 5px;\r
+ border-left-color: #000000;\r
+}\r
+.tooltip.bottom .tooltip-arrow {\r
+ top: 0;\r
+ left: 50%;\r
+ margin-left: -5px;\r
+ border-width: 0 5px 5px;\r
+ border-bottom-color: #000000;\r
+}\r
+.tooltip.bottom-left .tooltip-arrow {\r
+ top: 0;\r
+ left: 5px;\r
+ border-width: 0 5px 5px;\r
+ border-bottom-color: #000000;\r
+}\r
+.tooltip.bottom-right .tooltip-arrow {\r
+ top: 0;\r
+ right: 5px;\r
+ border-width: 0 5px 5px;\r
+ border-bottom-color: #000000;\r
+}\r
+.popover {\r
+ position: absolute;\r
+ top: 0;\r
+ left: 0;\r
+ z-index: 1010;\r
+ display: none;\r
+ max-width: 276px;\r
+ padding: 1px;\r
+ text-align: left;\r
+ background-color: #ffffff;\r
+ background-clip: padding-box;\r
+ border: 1px solid #cccccc;\r
+ border: 1px solid rgba(0, 0, 0, 0.2);\r
+ border-radius: 0px;\r
+ -webkit-box-shadow: 0 5px 10px rgba(0, 0, 0, 0.2);\r
+ box-shadow: 0 5px 10px rgba(0, 0, 0, 0.2);\r
+ white-space: normal;\r
+}\r
+.popover.top {\r
+ margin-top: -10px;\r
+}\r
+.popover.right {\r
+ margin-left: 10px;\r
+}\r
+.popover.bottom {\r
+ margin-top: 10px;\r
+}\r
+.popover.left {\r
+ margin-left: -10px;\r
+}\r
+.popover-title {\r
+ margin: 0;\r
+ padding: 8px 14px;\r
+ font-size: 14px;\r
+ font-weight: normal;\r
+ line-height: 18px;\r
+ background-color: #f7f7f7;\r
+ border-bottom: 1px solid #ebebeb;\r
+ border-radius: 5px 5px 0 0;\r
+}\r
+.popover-content {\r
+ padding: 9px 14px;\r
+}\r
+.popover > .arrow,\r
+.popover > .arrow:after {\r
+ position: absolute;\r
+ display: block;\r
+ width: 0;\r
+ height: 0;\r
+ border-color: transparent;\r
+ border-style: solid;\r
+}\r
+.popover > .arrow {\r
+ border-width: 11px;\r
+}\r
+.popover > .arrow:after {\r
+ border-width: 10px;\r
+ content: "";\r
+}\r
+.popover.top > .arrow {\r
+ left: 50%;\r
+ margin-left: -11px;\r
+ border-bottom-width: 0;\r
+ border-top-color: #999999;\r
+ border-top-color: rgba(0, 0, 0, 0.25);\r
+ bottom: -11px;\r
+}\r
+.popover.top > .arrow:after {\r
+ content: " ";\r
+ bottom: 1px;\r
+ margin-left: -10px;\r
+ border-bottom-width: 0;\r
+ border-top-color: #ffffff;\r
+}\r
+.popover.right > .arrow {\r
+ top: 50%;\r
+ left: -11px;\r
+ margin-top: -11px;\r
+ border-left-width: 0;\r
+ border-right-color: #999999;\r
+ border-right-color: rgba(0, 0, 0, 0.25);\r
+}\r
+.popover.right > .arrow:after {\r
+ content: " ";\r
+ left: 1px;\r
+ bottom: -10px;\r
+ border-left-width: 0;\r
+ border-right-color: #ffffff;\r
+}\r
+.popover.bottom > .arrow {\r
+ left: 50%;\r
+ margin-left: -11px;\r
+ border-top-width: 0;\r
+ border-bottom-color: #999999;\r
+ border-bottom-color: rgba(0, 0, 0, 0.25);\r
+ top: -11px;\r
+}\r
+.popover.bottom > .arrow:after {\r
+ content: " ";\r
+ top: 1px;\r
+ margin-left: -10px;\r
+ border-top-width: 0;\r
+ border-bottom-color: #ffffff;\r
+}\r
+.popover.left > .arrow {\r
+ top: 50%;\r
+ right: -11px;\r
+ margin-top: -11px;\r
+ border-right-width: 0;\r
+ border-left-color: #999999;\r
+ border-left-color: rgba(0, 0, 0, 0.25);\r
+}\r
+.popover.left > .arrow:after {\r
+ content: " ";\r
+ right: 1px;\r
+ border-right-width: 0;\r
+ border-left-color: #ffffff;\r
+ bottom: -10px;\r
+}\r
+.carousel {\r
+ position: relative;\r
+}\r
+.carousel-inner {\r
+ position: relative;\r
+ overflow: hidden;\r
+ width: 100%;\r
+}\r
+.carousel-inner > .item {\r
+ display: none;\r
+ position: relative;\r
+ -webkit-transition: 0.6s ease-in-out left;\r
+ transition: 0.6s ease-in-out left;\r
+}\r
+.carousel-inner > .item > img,\r
+.carousel-inner > .item > a > img {\r
+ line-height: 1;\r
+}\r
+.carousel-inner > .active,\r
+.carousel-inner > .next,\r
+.carousel-inner > .prev {\r
+ display: block;\r
+}\r
+.carousel-inner > .active {\r
+ left: 0;\r
+}\r
+.carousel-inner > .next,\r
+.carousel-inner > .prev {\r
+ position: absolute;\r
+ top: 0;\r
+ width: 100%;\r
+}\r
+.carousel-inner > .next {\r
+ left: 100%;\r
+}\r
+.carousel-inner > .prev {\r
+ left: -100%;\r
+}\r
+.carousel-inner > .next.left,\r
+.carousel-inner > .prev.right {\r
+ left: 0;\r
+}\r
+.carousel-inner > .active.left {\r
+ left: -100%;\r
+}\r
+.carousel-inner > .active.right {\r
+ left: 100%;\r
+}\r
+.carousel-control {\r
+ position: absolute;\r
+ top: 0;\r
+ left: 0;\r
+ bottom: 0;\r
+ width: 15%;\r
+ opacity: 0.5;\r
+ filter: alpha(opacity=50);\r
+ font-size: 20px;\r
+ color: #ffffff;\r
+ text-align: center;\r
+ text-shadow: 0 1px 2px rgba(0, 0, 0, 0.6);\r
+}\r
+.carousel-control.left {\r
+ background-image: -webkit-linear-gradient(left, color-stop(rgba(0, 0, 0, 0.5) 0%), color-stop(rgba(0, 0, 0, 0.0001) 100%));\r
+ background-image: linear-gradient(to right, rgba(0, 0, 0, 0.5) 0%, rgba(0, 0, 0, 0.0001) 100%);\r
+ background-repeat: repeat-x;\r
+ filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#80000000', endColorstr='#00000000', GradientType=1);\r
+}\r
+.carousel-control.right {\r
+ left: auto;\r
+ right: 0;\r
+ background-image: -webkit-linear-gradient(left, color-stop(rgba(0, 0, 0, 0.0001) 0%), color-stop(rgba(0, 0, 0, 0.5) 100%));\r
+ background-image: linear-gradient(to right, rgba(0, 0, 0, 0.0001) 0%, rgba(0, 0, 0, 0.5) 100%);\r
+ background-repeat: repeat-x;\r
+ filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#00000000', endColorstr='#80000000', GradientType=1);\r
+}\r
+.carousel-control:hover,\r
+.carousel-control:focus {\r
+ outline: none;\r
+ color: #ffffff;\r
+ text-decoration: none;\r
+ opacity: 0.9;\r
+ filter: alpha(opacity=90);\r
+}\r
+.carousel-control .icon-prev,\r
+.carousel-control .icon-next,\r
+.carousel-control .glyphicon-chevron-left,\r
+.carousel-control .glyphicon-chevron-right {\r
+ position: absolute;\r
+ top: 50%;\r
+ z-index: 5;\r
+ display: inline-block;\r
+}\r
+.carousel-control .icon-prev,\r
+.carousel-control .glyphicon-chevron-left {\r
+ left: 50%;\r
+}\r
+.carousel-control .icon-next,\r
+.carousel-control .glyphicon-chevron-right {\r
+ right: 50%;\r
+}\r
+.carousel-control .icon-prev,\r
+.carousel-control .icon-next {\r
+ width: 20px;\r
+ height: 20px;\r
+ margin-top: -10px;\r
+ margin-left: -10px;\r
+ font-family: serif;\r
+}\r
+.carousel-control .icon-prev:before {\r
+ content: '\2039';\r
+}\r
+.carousel-control .icon-next:before {\r
+ content: '\203a';\r
+}\r
+.carousel-indicators {\r
+ position: absolute;\r
+ bottom: 10px;\r
+ left: 50%;\r
+ z-index: 15;\r
+ width: 60%;\r
+ margin-left: -30%;\r
+ padding-left: 0;\r
+ list-style: none;\r
+ text-align: center;\r
+}\r
+.carousel-indicators li {\r
+ display: inline-block;\r
+ width: 10px;\r
+ height: 10px;\r
+ margin: 1px;\r
+ text-indent: -999px;\r
+ border: 1px solid #ffffff;\r
+ border-radius: 10px;\r
+ cursor: pointer;\r
+ background-color: #000 \9;\r
+ background-color: rgba(0, 0, 0, 0);\r
+}\r
+.carousel-indicators .active {\r
+ margin: 0;\r
+ width: 12px;\r
+ height: 12px;\r
+ background-color: #ffffff;\r
+}\r
+.carousel-caption {\r
+ position: absolute;\r
+ left: 15%;\r
+ right: 15%;\r
+ bottom: 20px;\r
+ z-index: 10;\r
+ padding-top: 20px;\r
+ padding-bottom: 20px;\r
+ color: #ffffff;\r
+ text-align: center;\r
+ text-shadow: 0 1px 2px rgba(0, 0, 0, 0.6);\r
+}\r
+.carousel-caption .btn {\r
+ text-shadow: none;\r
+}\r
+@media screen and (min-width: 768px) {\r
+ .carousel-control .glyphicons-chevron-left,\r
+ .carousel-control .glyphicons-chevron-right,\r
+ .carousel-control .icon-prev,\r
+ .carousel-control .icon-next {\r
+ width: 30px;\r
+ height: 30px;\r
+ margin-top: -15px;\r
+ margin-left: -15px;\r
+ font-size: 30px;\r
+ }\r
+ .carousel-caption {\r
+ left: 20%;\r
+ right: 20%;\r
+ padding-bottom: 30px;\r
+ }\r
+ .carousel-indicators {\r
+ bottom: 20px;\r
+ }\r
+}\r
+.clearfix:before,\r
+.clearfix:after,\r
+.container:before,\r
+.container:after,\r
+.container-fluid:before,\r
+.container-fluid:after,\r
+.row:before,\r
+.row:after,\r
+.form-horizontal .form-group:before,\r
+.form-horizontal .form-group:after,\r
+.btn-toolbar:before,\r
+.btn-toolbar:after,\r
+.btn-group-vertical > .btn-group:before,\r
+.btn-group-vertical > .btn-group:after,\r
+.nav:before,\r
+.nav:after,\r
+.navbar:before,\r
+.navbar:after,\r
+.navbar-header:before,\r
+.navbar-header:after,\r
+.navbar-collapse:before,\r
+.navbar-collapse:after,\r
+.pager:before,\r
+.pager:after,\r
+.panel-body:before,\r
+.panel-body:after,\r
+.modal-footer:before,\r
+.modal-footer:after {\r
+ content: " ";\r
+ display: table;\r
+}\r
+.clearfix:after,\r
+.container:after,\r
+.container-fluid:after,\r
+.row:after,\r
+.form-horizontal .form-group:after,\r
+.btn-toolbar:after,\r
+.btn-group-vertical > .btn-group:after,\r
+.nav:after,\r
+.navbar:after,\r
+.navbar-header:after,\r
+.navbar-collapse:after,\r
+.pager:after,\r
+.panel-body:after,\r
+.modal-footer:after {\r
+ clear: both;\r
+}\r
+.center-block {\r
+ display: block;\r
+ margin-left: auto;\r
+ margin-right: auto;\r
+}\r
+.pull-right {\r
+ float: right !important;\r
+}\r
+.pull-left {\r
+ float: left !important;\r
+}\r
+.hide {\r
+ display: none !important;\r
+}\r
+.show {\r
+ display: block !important;\r
+}\r
+.invisible {\r
+ visibility: hidden;\r
+}\r
+.text-hide {\r
+ font: 0/0 a;\r
+ color: transparent;\r
+ text-shadow: none;\r
+ background-color: transparent;\r
+ border: 0;\r
+}\r
+.hidden {\r
+ display: none !important;\r
+ visibility: hidden !important;\r
+}\r
+.affix {\r
+ position: fixed;\r
+}\r
+@-ms-viewport {\r
+ width: device-width;\r
+}\r
+.visible-xs,\r
+.visible-sm,\r
+.visible-md,\r
+.visible-lg {\r
+ display: none !important;\r
+}\r
+@media (max-width: 767px) {\r
+ .visible-xs {\r
+ display: block !important;\r
+ }\r
+ table.visible-xs {\r
+ display: table;\r
+ }\r
+ tr.visible-xs {\r
+ display: table-row !important;\r
+ }\r
+ th.visible-xs,\r
+ td.visible-xs {\r
+ display: table-cell !important;\r
+ }\r
+}\r
+@media (min-width: 768px) and (max-width: 991px) {\r
+ .visible-sm {\r
+ display: block !important;\r
+ }\r
+ table.visible-sm {\r
+ display: table;\r
+ }\r
+ tr.visible-sm {\r
+ display: table-row !important;\r
+ }\r
+ th.visible-sm,\r
+ td.visible-sm {\r
+ display: table-cell !important;\r
+ }\r
+}\r
+@media (min-width: 992px) and (max-width: 1199px) {\r
+ .visible-md {\r
+ display: block !important;\r
+ }\r
+ table.visible-md {\r
+ display: table;\r
+ }\r
+ tr.visible-md {\r
+ display: table-row !important;\r
+ }\r
+ th.visible-md,\r
+ td.visible-md {\r
+ display: table-cell !important;\r
+ }\r
+}\r
+@media (min-width: 1200px) {\r
+ .visible-lg {\r
+ display: block !important;\r
+ }\r
+ table.visible-lg {\r
+ display: table;\r
+ }\r
+ tr.visible-lg {\r
+ display: table-row !important;\r
+ }\r
+ th.visible-lg,\r
+ td.visible-lg {\r
+ display: table-cell !important;\r
+ }\r
+}\r
+@media (max-width: 767px) {\r
+ .hidden-xs {\r
+ display: none !important;\r
+ }\r
+}\r
+@media (min-width: 768px) and (max-width: 991px) {\r
+ .hidden-sm {\r
+ display: none !important;\r
+ }\r
+}\r
+@media (min-width: 992px) and (max-width: 1199px) {\r
+ .hidden-md {\r
+ display: none !important;\r
+ }\r
+}\r
+@media (min-width: 1200px) {\r
+ .hidden-lg {\r
+ display: none !important;\r
+ }\r
+}\r
+.visible-print {\r
+ display: none !important;\r
+}\r
+@media print {\r
+ .visible-print {\r
+ display: block !important;\r
+ }\r
+ table.visible-print {\r
+ display: table;\r
+ }\r
+ tr.visible-print {\r
+ display: table-row !important;\r
+ }\r
+ th.visible-print,\r
+ td.visible-print {\r
+ display: table-cell !important;\r
+ }\r
+}\r
+@media print {\r
+ .hidden-print {\r
+ display: none !important;\r
+ }\r
+}\r
+ \r
--- /dev/null
+<div class='container-fluid'>
+ <div class='page-header'>
+ <h2><entity-signature mentity='mentity.intro'/></h2>
+ <entity-link mentity='mentity.mpackage' /> :: {{mentity.name}}
+ </div>
+
+ <ul class='nav nav-tabs'>
+ <li class='active'>
+ <a data-toggle='tab' data-target='#doc'>
+ <span class='glyphicon glyphicon-book'/> Doc
+ </a>
+ </li>
+ </ul>
+
+ <div class='tab-content'>
+ <div class='tab-pane fade in active' id='doc'>
+ <entity-doc mentity='mentity.intro'/>
+
+ <entity-list list-title='Parents'
+ list-entities='mentity.parents'
+ list-object-filter='{}' />
+
+ <entity-list list-title='Constructors'
+ list-entities='mentity.all_mproperties'
+ list-object-filter='{is_init: true}' />
+
+ <entity-list list-title='Introduced properties'
+ list-entities='mentity.intro_mproperties'
+ list-object-filter='{is_init: "!true"}' />
+
+ <entity-list list-title='Redefined properties'
+ list-entities='mentity.redef_mproperties'
+ list-object-filter='{is_init: "!true"}' />
+ </div>
+ </div>
+</div>
--- /dev/null
+<div class='container-fluid'>
+ <div class='page-header'>
+ <h2><entity-signature mentity='mentity'/></h2>
+ <entity-link mentity='mentity.mpackage' />
+ :: <entity-link mentity='mentity.mmodule' />
+ :: {{mentity.name}}
+ </div>
+
+ <ul class='nav nav-tabs' role='tablist'>
+ <li class='warning'>
+ <a ng-href='{{mentity.mclass.web_url}}'>
+ <span class='glyphicon glyphicon-chevron-left'/> Go to class
+ </a>
+ </li>
+ </ul>
+</div>
--- /dev/null
+<div class='container-fluid'>
+ <div class='page-header'>
+ <h2><entity-signature mentity='mentity' /></h2>
+ <entity-link mentity='mentity.mpackage' /> :: {{mentity.name}}
+ </div>
+
+ <ul class='nav nav-tabs'>
+ <li class='active'>
+ <a data-toggle='tab' data-target='#doc'>
+ <span class='glyphicon glyphicon-book'/> Doc
+ </a>
+ </li>
+ </ul>
+
+ <div class='tab-content'>
+ <div class='tab-pane fade in active' id='doc'>
+ <entity-doc mentity='mentity'/>
+
+ <entity-list list-title='Parent group' list-entities='[mentity.parent]'
+ list-object-filter='{}' ng-if='mentity.parent' />
+
+ <entity-list list-title='Subgroups' list-entities='mentity.mgroups'
+ list-object-filter='{}' />
+
+ <entity-list list-title='Modules' list-entities='mentity.mmodules'
+ list-object-filter='{}' />
+ </div>
+ </div>
+ </div>
+</div>
--- /dev/null
+<h1>Hello nitweb!</h1>
--- /dev/null
+<div class='container-fluid'>
+ <div class='page-header'>
+ <h2><entity-signature mentity='mentity'/></h2>
+ <entity-link mentity='mentity.mpackage' /> :: {{mentity.name}}
+ </div>
+
+ <ul class='nav nav-tabs'>
+ <li class='active'>
+ <a data-toggle='tab' data-target='#doc'>
+ <span class='glyphicon glyphicon-book'/> Doc
+ </a>
+ </li>
+ </ul>
+
+ <div class='tab-content'>
+ <div role='tabpanel' class='tab-pane fade in active' id='doc'>
+ <entity-doc mentity='mentity'/>
+
+ <entity-list list-title='Imported modules' list-entities='mentity.imports'
+ list-object-filter='{}' />
+
+ <entity-list list-title='Introduced classes' list-entities='mentity.intro_mclasses'
+ list-object-filter='{}' />
+
+ <entity-list list-title='Class redefinitions' list-entities='mentity.redef_mclassdefs'
+ list-object-filter='{}' />
+
+ </div>
+ </div>
+</div>
--- /dev/null
+<div class='container-fluid'>
+ <div class='page-header'>
+ <h2><entity-signature mentity='mentity'/></h2>
+ </div>
+
+ <ul class='nav nav-tabs' role='tablist'>
+ <li role='presentation' class='active'>
+ <a data-toggle='tab' role='tab' data-target='#doc' aria-controls="doc">
+ <span class='glyphicon glyphicon-book'/> Doc
+ </a>
+ </li>
+ </ul>
+
+ <div class='tab-content'>
+ <div role='tabpanel' class='tab-pane fade in active' id='doc'>
+ <entity-doc mentity='mentity'/>
+
+ <entity-list list-title='Groups' list-entities='mentity.mgroups'
+ list-object-filter='{}' />
+ </div>
+ </div>
+</div>
--- /dev/null
+<div class='container-fluid'>
+
+ <div class='page-header'>
+ <h2><entity-signature mentity='mentity'/></h2>
+ <entity-link mentity='mentity.mpackage' />
+ :: <entity-link mentity='mentity.mmodule' />
+ :: <entity-link mentity='mentity.mclassdef' />
+ :: {{mentity.name}}
+ </div>
+
+ <ul class='nav nav-tabs'>
+ <li class='warning'>
+ <a href='{{mentity.mproperty.web_url}}'>
+ <span class='glyphicon glyphicon-chevron-left'/> Go to property
+ </a>
+ </li>
+ </ul>
+</div>
--- /dev/null
+<div class='container-fluid'>
+
+ <div class='page-header'>
+ <h2><entity-signature mentity='mentity.intro'/></h2>
+ <entity-link mentity='mentity.mpackage' />
+ :: <entity-link mentity='mentity.intro_mclassdef' />
+ :: {{mentity.name}}
+ </div>
+
+ <ul class='nav nav-tabs'>
+ <li class='active'>
+ <a data-toggle='tab' data-target='#doc'>
+ <span class='glyphicon glyphicon-book'/> Doc
+ </a>
+ </li>
+ </ul>
+
+ <div class='tab-content'>
+ <div role='tabpanel' class='tab-pane fade in active' id='doc'>
+ <entity-doc mentity='mentity.intro'/>
+ </div>
+ </div>
+</div>
var doc_score = 0.0
for g in mpackage.mgroups do
mmodules += g.mmodules.length
- entity_score += 1.0
- if g.mdoc != null then doc_score += 1.0
+ var gs = 1.0
+ entity_score += gs
+ if g.mdoc != null then doc_score += gs
for m in g.mmodules do
var source = m.location.file
if source != null then
loc += file.line_starts.length - 1
end
end
- entity_score += 1.0
- if m.mdoc != null then doc_score += 1.0
+ var ms = gs
+ if m.is_test_suite then ms /= 100.0
+ entity_score += ms
+ if m.mdoc != null then doc_score += ms else ms /= 10.0
for cd in m.mclassdefs do
- var s = 0.2
- if not cd.is_intro then s /= 10.0
- if not cd.mclass.visibility <= private_visibility then s /= 10.0
- entity_score += s
- if cd.mdoc != null then doc_score += s
+ var cs = ms * 0.2
+ if not cd.is_intro then cs /= 100.0
+ if not cd.mclass.visibility <= private_visibility then cs /= 100.0
+ entity_score += cs
+ if cd.mdoc != null then doc_score += cs
mclasses += 1
for pd in cd.mpropdefs do
- s = 0.1
- if not pd.is_intro then s /= 10.0
- if not pd.mproperty.visibility <= private_visibility then s /= 10.0
- entity_score += s
- if pd.mdoc != null then doc_score += s
+ var ps = ms * 0.1
+ if not pd.is_intro then ps /= 100.0
+ if not pd.mproperty.visibility <= private_visibility then ps /= 100.0
+ entity_score += ps
+ if pd.mdoc != null then doc_score += ps
if not pd isa MMethodDef then continue
mmethods += 1
end
var opt_source = new OptionString("Format to link source code (%f for filename, " +
"%l for first line, %L for last line)", "--source")
- # Directory where the CSS and JS is stored.
- var opt_sharedir = new OptionString("Directory containing nitdoc assets", "--sharedir")
-
# Use a shareurl instead of copy shared files.
#
# This is usefull if you don't want to store the Nitdoc templates with your
super
option_context.add_option(
- opt_source, opt_sharedir, opt_shareurl, opt_custom_title,
+ opt_source, opt_share_dir, opt_shareurl, opt_custom_title,
opt_custom_footer, opt_custom_intro, opt_custom_brand,
opt_github_upstream, opt_github_base_sha1, opt_github_gitdir,
opt_piwik_tracker, opt_piwik_site_id,
var output_dir = ctx.output_dir
if not output_dir.file_exists then output_dir.mkdir
# locate share dir
- var sharedir = ctx.opt_sharedir.value
- if sharedir == null then
- var dir = ctx.nit_dir
- sharedir = dir/"share/nitdoc"
- if not sharedir.file_exists then
- print "Error: cannot locate nitdoc share files. Uses --sharedir or envvar NIT_DIR"
- abort
- end
- end
+ var sharedir = ctx.share_dir / "nitdoc"
# copy shared files
if ctx.opt_shareurl.value == null then
sys.system("cp -r -- {sharedir.to_s.escape_to_sh}/* {output_dir.to_s.escape_to_sh}/")
srcs.add_all mmodule.ffi_files
# Compiler options specific to this module
- var ldflags = mmodule.ldflags[""].join(" ")
+ var ldflags_array = mmodule.ldflags[""]
+ if ldflags_array.has("-lrt") and system("sh -c 'uname -s 2>/dev/null || echo not' | grep Darwin >/dev/null") == 0 then
+ # Remove -lrt on OS X
+ ldflags_array.remove "-lrt"
+ end
+ var ldflags = ldflags_array.join(" ")
# Protect pkg-config
var pkgconfigs = mmodule.pkgconfigs
import ordered_tree
private import more_collections
+redef class MEntity
+ # The visibility of the MEntity.
+ #
+ # MPackages, MGroups and MModules are always public.
+ # The visibility of `MClass` and `MProperty` is defined by the keyword used.
+ # `MClassDef` and `MPropDef` return the visibility of `MClass` and `MProperty`.
+ fun visibility: MVisibility do return public_visibility
+end
+
redef class Model
# All known classes
var mclasses = new Array[MClass]
# The visibility of the class
# In Nit, the visibility of a class cannot evolve in refinements
- var visibility: MVisibility
+ redef var visibility
init
do
# Is `self` and abstract class?
var is_abstract: Bool is lazy do return kind == abstract_kind
+
+ redef fun mdoc_or_fallback do return intro.mdoc_or_fallback
end
redef var location: Location
+ redef fun visibility do return mclass.visibility
+
# Internal name combining the module and the class
# Example: "mymodule$MyClass"
redef var to_s is noinit
redef var location
+ redef fun mdoc_or_fallback do return intro.mdoc_or_fallback
+
# The canonical name of the property.
#
# It is currently the short-`name` prefixed by the short-name of the class and the full-name of the module.
end
# The visibility of the property
- var visibility: MVisibility
+ redef var visibility
# Is the property usable as an initializer?
var is_autoinit = false is writable
redef var location: Location
+ redef fun visibility do return mproperty.visibility
+
init
do
mclassdef.mpropdefs.add(self)
var mmodules = new HashSet[MModule]
mmodules.add self
mmodules.add_all collect_ancestors(view)
- mmodules.add_all collect_parents(view)
- mmodules.add_all collect_children(view)
mmodules.add_all collect_descendants(view)
return view.mmodules_poset(mmodules)
end
return res
end
+ # Build a class hierarchy poset for `self` based on its ancestors and descendants.
+ fun hierarchy_poset(mainmodule: MModule, view: ModelView): POSet[MClass] do
+ var mclasses = new HashSet[MClass]
+ mclasses.add self
+ mclasses.add_all collect_ancestors(view)
+ mclasses.add_all collect_descendants(view)
+ return view.mclasses_poset(mainmodule, mclasses)
+ end
+
# Collect all mproperties introduced in 'self' with `visibility >= min_visibility`.
fun collect_intro_mproperties(view: ModelView): Set[MProperty] do
var set = new HashSet[MProperty]
obj["class_name"] = class_name
obj["full_name"] = full_name
obj["mdoc"] = mdoc_or_fallback
+ obj["visibility"] = visibility
+ obj["location"] = location
var modifiers = new JsonArray
for modifier in collect_modifiers do
modifiers.add modifier
redef fun json do
var obj = super
- obj["visibility"] = public_visibility
if ini != null then
obj["ini"] = new JsonObject.from(ini.as(not null).to_map)
end
redef class MGroup
redef fun json do
var obj = super
- obj["visibility"] = public_visibility
obj["is_root"] = is_root
obj["mpackage"] = to_mentity_ref(mpackage)
obj["default_mmodule"] = to_mentity_ref(default_mmodule)
redef class MModule
redef fun json do
var obj = super
- obj["location"] = location
- obj["visibility"] = public_visibility
obj["mpackage"] = to_mentity_ref(mpackage)
obj["mgroup"] = to_mentity_ref(mgroup)
obj["intro_mclasses"] = to_mentity_refs(intro_mclasses)
redef class MClass
redef fun json do
var obj = super
- obj["visibility"] = visibility
var arr = new JsonArray
for mparameter in mparameters do arr.add mparameter
obj["mparameters"] = arr
redef class MClassDef
redef fun json do
var obj = super
- obj["visibility"] = mclass.visibility
- obj["location"] = location
obj["is_intro"] = is_intro
var arr = new JsonArray
for mparameter in mclass.mparameters do arr.add mparameter
redef class MProperty
redef fun json do
var obj = super
- obj["visibility"] = visibility
obj["intro"] = to_mentity_ref(intro)
obj["intro_mclassdef"] = to_mentity_ref(intro_mclassdef)
obj["mpropdefs"] = to_mentity_refs(mpropdefs)
redef class MPropDef
redef fun json do
var obj = super
- obj["visibility"] = mproperty.visibility
- obj["location"] = location
obj["is_intro"] = is_intro
obj["mclassdef"] = to_mentity_ref(mclassdef)
obj["mproperty"] = to_mentity_ref(mproperty)
# See the specific implementation in the subclasses.
fun visit_all(v: ModelVisitor) do end
- private fun accept_visibility(min_visibility: nullable MVisibility): Bool do return true
+ private fun accept_visibility(min_visibility: nullable MVisibility): Bool do
+ if min_visibility == null then return true
+ return visibility >= min_visibility
+ end
end
redef class Model
end
end
-redef class MClass
- redef fun accept_visibility(min_visibility) do
- if min_visibility == null then return true
- return visibility >= min_visibility
- end
-end
-
redef class MClassDef
# Visit all the classes and class definitions of the module.
#
v.enter_visit(x)
end
end
-
- redef fun accept_visibility(min_visibility) do
- if min_visibility == null then return true
- return mclass.visibility >= min_visibility
- end
-end
-
-redef class MProperty
- redef fun accept_visibility(min_visibility) do
- if min_visibility == null then return true
- return visibility >= min_visibility
- end
-end
-
-redef class MPropDef
- redef fun accept_visibility(min_visibility) do
- if min_visibility == null then return true
- return mproperty.visibility >= min_visibility
- end
end
end
"NIT_TESTING".setenv("true")
+"NIT_TESTING_ID".setenv(pid.to_s)
+"SRAND".setenv("0")
var test_dir = toolcontext.test_dir
test_dir.mkdir
var file = toolcontext.opt_output.value
if file == null then file = "nitunit.xml"
page.write_to_file(file)
-# print docunits results
-print "DocUnits:"
-if modelbuilder.unit_entities == 0 then
- print "No doc units found"
-else if modelbuilder.failed_entities == 0 and not toolcontext.opt_noact.value then
- print "DocUnits Success"
+
+# Print results
+printn "Docunits: Entities: {modelbuilder.total_entities}; Documented ones: {modelbuilder.doc_entities}; With nitunits: {modelbuilder.unit_entities}"
+if modelbuilder.unit_entities == 0 or toolcontext.opt_noact.value then
+ print ""
+else
+ printn "; Failures: "
+ var cpt = modelbuilder.failed_entities
+ if toolcontext.opt_no_color.value then
+ print cpt
+ else if cpt == 0 then
+ print "0".green.bold
+ else
+ print cpt.to_s.red.bold
+ end
end
-print "Entities: {modelbuilder.total_entities}; Documented ones: {modelbuilder.doc_entities}; With nitunits: {modelbuilder.unit_entities}; Failures: {modelbuilder.failed_entities}"
-# print testsuites results
-print "\nTestSuites:"
-if modelbuilder.total_tests == 0 then
- print "No test cases found"
-else if modelbuilder.failed_tests == 0 and not toolcontext.opt_noact.value then
- print "TestSuites Success"
+printn "Test suites: Classes: {modelbuilder.total_classes}; Test Cases: {modelbuilder.total_tests}"
+if modelbuilder.total_tests == 0 or toolcontext.opt_noact.value then
+ print ""
+else
+ printn "; Failures: "
+ var cpt = modelbuilder.failed_tests
+ if toolcontext.opt_no_color.value then
+ print cpt
+ else if cpt == 0 then
+ print "0".green.bold
+ else
+ print cpt.to_s.red.bold
+ end
end
-print "Class suites: {modelbuilder.total_classes}; Test Cases: {modelbuilder.total_tests}; Failures: {modelbuilder.failed_tests}"
+
+var total = modelbuilder.unit_entities + modelbuilder.total_tests
+var fail = modelbuilder.failed_entities + modelbuilder.failed_tests
+if toolcontext.opt_noact.value then
+ # nothing
+else if total == 0 then
+ var head = "[NOTHING]"
+ if not toolcontext.opt_no_color.value then
+ head = head.yellow
+ end
+ print "{head} No unit tests to execute."
+else if fail == 0 then
+ var head = "[SUCCESS]"
+ if not toolcontext.opt_no_color.value then
+ head = head.green.bold
+ end
+ print "{head} All {total} tests passed."
+else
+ var head = "[FAILURE]"
+ if not toolcontext.opt_no_color.value then
+ head = head.red.bold
+ end
+ print "{head} {fail}/{total} tests failed."
+
+ print "`{test_dir}` is not removed for investigation."
+ exit 1
+end
+
+test_dir.rmdir
var port = toolcontext.opt_port.value
var app = new App
- app.use("/random", new RandomAction(model))
- app.use("/doc/:namespace", new DocAction(model, modelbuilder))
- app.use("/code/:namespace", new CodeAction(model, modelbuilder))
- app.use("/search/:namespace", new SearchAction(model))
- app.use("/uml/:namespace", new UMLDiagramAction(model, mainmodule))
- app.use("/", new TreeAction(model))
+
+ app.use("/api", new APIRouter(model, modelbuilder, mainmodule))
+ app.use("/doc/:namespace", new DocAction(model, mainmodule, modelbuilder))
+ app.use("/*", new StaticHandler(toolcontext.share_dir / "nitweb", "index.html"))
app.listen(host, port.to_i)
end
add_cast(paramtype)
end
+ if mmethoddef.is_abstract then continue
+
var npropdef = modelbuilder.mpropdef2node(mmethoddef)
if npropdef isa AClassdef then
if not check_depth(rt) then continue
#print "{ot}/{t} -> {rt}"
live_types.add(rt)
- todo_types.add(rt)
+ # unshift means a deep-first visit.
+ # So that the `check_depth` limit is reached sooner.
+ todo_types.unshift(rt)
end
end
#print "MType {live_types.length}: {live_types.join(", ")}"
import modelize
private import parser_util
+import html
+import console
redef class ToolContext
# opt --full
# Working directory for testing.
fun test_dir: String do
var dir = opt_dir.value
- if dir == null then return ".nitunit"
+ if dir == null then return "nitunit.out"
return dir
end
#
# Default: 10 CPU minute
var ulimit_usertime = 600 is writable
+
+ # Show a single-line status to use as a progression.
+ #
+ # Note that the line starts with `'\r'` and is not ended by a `'\n'`.
+ # So it is expected that:
+ # * no other output is printed between two calls
+ # * the last `show_unit_status` is followed by a new-line
+ fun show_unit_status(name: String, tests: SequenceRead[UnitTest], more_message: nullable String)
+ do
+ var esc = 27.code_point.to_s
+ var line = "\r{esc}[K* {name} ["
+ var done = tests.length
+ for t in tests do
+ if not t.is_done then
+ line += " "
+ done -= 1
+ else if t.error == null then
+ line += ".".green.bold
+ else
+ line += "X".red.bold
+ end
+ end
+
+ if opt_no_color.value then
+ if done == 0 then
+ print "* {name} ({tests.length} tests)"
+ end
+ return
+ end
+
+ line += "] {done}/{tests.length}"
+ if more_message != null then
+ line += " " + more_message
+ end
+ printn "{line}"
+ end
+
+ # Shoe the full description of the test-case.
+ #
+ # The output honors `--no-color`.
+ #
+ # `more message`, if any, is added after the error message.
+ fun show_unit(test: UnitTest, more_message: nullable String) do
+ print test.to_screen(more_message, not opt_no_color.value)
+ end
+end
+
+# A unit test is an elementary test discovered, run and reported by nitunit.
+#
+# This class factorizes `DocUnit` and `TestCase`.
+abstract class UnitTest
+ # The name of the unit to show in messages
+ fun full_name: String is abstract
+
+ # The location of the unit test to show in messages.
+ fun location: Location is abstract
+
+ # Flag that indicates if the unit test was compiled/run.
+ var is_done: Bool = false is writable
+
+ # Error message occurred during test-case execution (or compilation).
+ #
+ # e.g.: `Runtime Error`
+ var error: nullable String = null is writable
+
+ # Was the test case executed at least once?
+ #
+ # This will indicate the status of the test (failture or error)
+ var was_exec = false is writable
+
+ # The raw output of the execution (or compilation)
+ #
+ # It merges the standard output and error output
+ var raw_output: nullable String = null is writable
+
+ # The location where the error occurred, if it makes sense.
+ var error_location: nullable Location = null is writable
+
+ # A colorful `[OK]` or `[KO]`.
+ fun status_tag(color: nullable Bool): String do
+ color = color or else true
+ if not is_done then
+ return "[ ]"
+ else if error != null then
+ var res = "[KO]"
+ if color then res = res.red.bold
+ return res
+ else
+ var res = "[OK]"
+ if color then res = res.green.bold
+ return res
+ end
+ end
+
+ # The full (color) description of the test-case.
+ #
+ # `more message`, if any, is added after the error message.
+ fun to_screen(more_message: nullable String, color: nullable Bool): String do
+ color = color or else true
+ var res
+ var error = self.error
+ if error != null then
+ if more_message != null then error += " " + more_message
+ var loc = error_location or else location
+ if color then
+ res = "{status_tag(color)} {full_name}\n {loc.to_s.yellow}: {error}\n{loc.colored_line("1;31")}"
+ else
+ res = "{status_tag(color)} {full_name}\n {loc}: {error}"
+ end
+ var output = self.raw_output
+ if output != null then
+ res += "\n Output\n\t{output.chomp.replace("\n", "\n\t")}\n"
+ end
+ else
+ res = "{status_tag(color)} {full_name}"
+ if more_message != null then res += more_message
+ end
+ return res
+ end
+
+ # Return a `<testcase>` XML node in format compatible with Jenkins unit tests.
+ fun to_xml: HTMLTag do
+ var tc = new HTMLTag("testcase")
+ tc.attr("classname", xml_classname)
+ tc.attr("name", xml_name)
+ var error = self.error
+ if error != null then
+ if was_exec then
+ tc.open("error").append(error)
+ else
+ tc.open("failure").append(error)
+ end
+ end
+ var output = self.raw_output
+ if output != null then
+ tc.open("system-err").append(output.trunc(8192).filter_nonprintable)
+ end
+ return tc
+ end
+
+ # The `classname` attribute of the XML format.
+ #
+ # NOTE: jenkins expects a '.' in the classname attr
+ #
+ # See to_xml
+ fun xml_classname: String is abstract
+
+ # The `name` attribute of the XML format.
+ #
+ # See to_xml
+ fun xml_name: String is abstract
end
redef class String
# The XML node associated to the module
var testsuite: HTMLTag
- # All blocks of code from a same `ADoc`
- var blocks = new Array[Buffer]
-
- # All failures from a same `ADoc`
- var failures = new Array[String]
+ # The name of the suite
+ var name: String
# Markdown processor used to parse markdown comments and extract code.
var mdproc = new MarkdownProcessor
# used to generate distinct names
var cpt = 0
+ # The last docunit extracted from a mdoc.
+ #
+ # Is used because a new code-block might just be added to it.
+ var last_docunit: nullable DocUnit = null
+
+ var xml_classname: String is noautoinit
+
+ var xml_name: String is noautoinit
+
# The entry point for a new `ndoc` node
# Fill `docunits` with new discovered unit of tests.
- #
- # `tc` (testcase) is the pre-filled XML node
- fun extract(mdoc: MDoc, tc: HTMLTag)
+ fun extract(mdoc: MDoc, xml_classname, xml_name: String)
do
- blocks.clear
- failures.clear
+ last_docunit = null
+ self.xml_classname = xml_classname
+ self.xml_name = xml_name
self.mdoc = mdoc
# Populate `blocks` from the markdown decorator
mdproc.process(mdoc.content.join("\n"))
-
- toolcontext.check_errors
-
- if not failures.is_empty then
- for msg in failures do
- var ne = new HTMLTag("failure")
- ne.attr("message", msg)
- tc.add ne
- toolcontext.modelbuilder.unit_entities += 1
- toolcontext.modelbuilder.failed_entities += 1
- end
- if blocks.is_empty then testsuite.add(tc)
- end
-
- if blocks.is_empty then return
- for block in blocks do
- docunits.add new DocUnit(mdoc, tc, block.write_to_string)
- end
end
# All extracted docunits
var docunits = new Array[DocUnit]
+ fun show_status(more_message: nullable String)
+ do
+ toolcontext.show_unit_status(name, docunits, more_message)
+ end
+
+ fun mark_done(du: DocUnit)
+ do
+ du.is_done = true
+ show_status(du.full_name + " " + du.status_tag)
+ end
+
# Execute all the docunits
fun run_tests
do
+ if docunits.is_empty then
+ return
+ end
+
var simple_du = new Array[DocUnit]
+ show_status
for du in docunits do
+ # Skip existing errors
+ if du.error != null then
+ mark_done(du)
+ continue
+ end
+
var ast = toolcontext.parse_something(du.block)
if ast isa AExpr then
simple_du.add du
end
test_simple_docunits(simple_du)
+
+ show_status
+ print ""
+
+ for du in docunits do
+ toolcontext.show_unit(du)
+ end
+
+ for du in docunits do
+ testsuite.add du.to_xml
+ end
end
# Executes multiples doc-units in a shared program.
i += 1
f.write("fun run_{i} do\n")
- f.write("# {du.testcase.attrs["name"]}\n")
+ f.write("# {du.full_name}\n")
f.write(du.block)
f.write("end\n")
end
i = 0
for du in dus do
- var tc = du.testcase
- toolcontext.modelbuilder.unit_entities += 1
i += 1
- toolcontext.info("Execute doc-unit {du.testcase.attrs["name"]} in {file} {i}", 1)
+ toolcontext.info("Execute doc-unit {du.full_name} in {file} {i}", 1)
var res2 = toolcontext.safe_exec("{file.to_program_name}.bin {i} >'{file}.out1' 2>&1 </dev/null")
+ du.was_exec = true
- f = new FileReader.open("{file}.out1")
- var n2
- n2 = new HTMLTag("system-err")
- tc.add n2
- var content = f.read_all
- var msg = content.trunc(8192).filter_nonprintable
- n2.append(msg)
- f.close
-
- n2 = new HTMLTag("system-out")
- tc.add n2
- n2.append(du.block)
+ var content = "{file}.out1".to_path.read_all
+ du.raw_output = content
if res2 != 0 then
- var ne = new HTMLTag("error")
- ne.attr("message", "Runtime error")
- tc.add ne
- toolcontext.warning(du.mdoc.location, "error", "ERROR: {tc.attrs["classname"]}.{tc.attrs["name"]} (in {file}): Runtime error\n{msg}")
+ du.error = "Runtime error in {file} with argument {i}"
toolcontext.modelbuilder.failed_entities += 1
end
- toolcontext.check_errors
-
- testsuite.add(tc)
+ mark_done(du)
end
end
# Used for docunits larger than a single block of code (with modules, classes, functions etc.)
fun test_single_docunit(du: DocUnit)
do
- var tc = du.testcase
- toolcontext.modelbuilder.unit_entities += 1
-
cpt += 1
var file = "{prefix}-{cpt}.nit"
- toolcontext.info("Execute doc-unit {tc.attrs["name"]} in {file}", 1)
+ toolcontext.info("Execute doc-unit {du.full_name} in {file}", 1)
var f
f = create_unitfile(file)
var res2 = 0
if res == 0 then
res2 = toolcontext.safe_exec("{file.to_program_name}.bin >'{file}.out1' 2>&1 </dev/null")
+ du.was_exec = true
end
- f = new FileReader.open("{file}.out1")
- var n2
- n2 = new HTMLTag("system-err")
- tc.add n2
- var content = f.read_all
- var msg = content.trunc(8192).filter_nonprintable
- n2.append(msg)
- f.close
-
- n2 = new HTMLTag("system-out")
- tc.add n2
- n2.append(du.block)
-
+ var content = "{file}.out1".to_path.read_all
+ du.raw_output = content
if res != 0 then
- var ne = new HTMLTag("failure")
- ne.attr("message", "Compilation Error")
- tc.add ne
- toolcontext.warning(du.mdoc.location, "failure", "FAILURE: {tc.attrs["classname"]}.{tc.attrs["name"]} (in {file}):\n{msg}")
+ du.error = "Compilation error in {file}"
toolcontext.modelbuilder.failed_entities += 1
else if res2 != 0 then
- var ne = new HTMLTag("error")
- ne.attr("message", "Runtime Error")
- tc.add ne
- toolcontext.warning(du.mdoc.location, "error", "ERROR: {tc.attrs["classname"]}.{tc.attrs["name"]} (in {file}):\n{msg}")
+ du.error = "Runtime error in {file}"
toolcontext.modelbuilder.failed_entities += 1
end
- toolcontext.check_errors
-
- testsuite.add(tc)
+ mark_done(du)
end
# Create and fill the header of a unit file `file`.
message = "Error: Invalid Nit code."
end
- executor.toolcontext.warning(location, "invalid-block", "{message} To suppress this message, enclose the block with a fence tagged `nitish` or `raw` (see `man nitdoc`).")
- executor.failures.add("{location}: {message}")
+ var du = new_docunit
+ du.block += code
+ du.error_location = location
+ du.error = message
+ executor.toolcontext.modelbuilder.failed_entities += 1
return
end
# Create a first block
# Or create a new block for modules that are more than a main part
- if executor.blocks.is_empty or ast isa AModule then
- executor.blocks.add(new Buffer)
+ var last_docunit = executor.last_docunit
+ if last_docunit == null or ast isa AModule then
+ last_docunit = new_docunit
+ executor.last_docunit = last_docunit
end
# Add it to the file
- executor.blocks.last.append code
+ last_docunit.block += code
+
+ # In order to retrieve precise positions,
+ # the real position of each line of the raw_content is stored.
+ # See `DocUnit::real_location`
+ line_offset -= loc.line_start - 1
+ for i in [loc.line_start..loc.line_end] do
+ last_docunit.lines.add i + line_offset
+ last_docunit.columns.add column_offset
+ end
+ end
+
+ # Return and register a new empty docunit
+ fun new_docunit: DocUnit
+ do
+ var mdoc = executor.mdoc
+ assert mdoc != null
+
+ var next_number = 0
+ var name = executor.xml_name
+ if executor.docunits.not_empty and executor.docunits.last.mdoc == mdoc then
+ next_number = executor.docunits.last.number + 1
+ name += "+" + next_number.to_s
+ end
+
+ var res = new DocUnit(mdoc, next_number, "", executor.xml_classname, name)
+ executor.docunits.add res
+ executor.toolcontext.modelbuilder.unit_entities += 1
+ return res
end
end
-# A unit-test to run
+# A unit-test extracted from some documentation.
+#
+# A docunit is extracted from the code-blocks of mdocs.
+# Each mdoc can contains more than one docunit, and a single docunit can be made of more that a single code-block.
class DocUnit
+ super UnitTest
+
# The doc that contains self
var mdoc: MDoc
- # The XML node that contains the information about the execution
- var testcase: HTMLTag
+ # The numbering of self in mdoc (starting with 0)
+ var number: Int
+
+ redef fun full_name do
+ var mentity = mdoc.original_mentity
+ if mentity != null then
+ return mentity.full_name
+ else
+ return xml_classname + "." + xml_name
+ end
+ end
- # The text of the code to execute
+ # The text of the code to execute.
+ #
+ # This is the verbatim content on one, or more, code-blocks from `mdoc`
var block: String
+
+ # For each line in `block`, the associated line in the mdoc
+ #
+ # Is used to give precise locations
+ var lines = new Array[Int]
+
+ # For each line in `block`, the associated column in the mdoc
+ #
+ # Is used to give precise locations
+ var columns = new Array[Int]
+
+ # The location of the whole docunit.
+ #
+ # If `self` is made of multiple code-blocks, then the location
+ # starts at the first code-books and finish at the last one, thus includes anything between.
+ redef var location is lazy do
+ return new Location(mdoc.location.file, lines.first, lines.last+1, columns.first+1, 0)
+ end
+
+ # Compute the real location of a node on the `ast` based on `mdoc.location`
+ #
+ # The result is basically: ast_location + markdown location of the piece + mdoc.location
+ #
+ # The fun is that a single docunit can be made of various pieces of code blocks.
+ fun real_location(ast_location: Location): Location
+ do
+ var mdoc = self.mdoc
+ var res = new Location(mdoc.location.file, lines[ast_location.line_start-1],
+ lines[ast_location.line_end-1],
+ columns[ast_location.line_start-1] + ast_location.column_start,
+ columns[ast_location.line_end-1] + ast_location.column_end)
+ return res
+ end
+
+ redef fun to_xml
+ do
+ var res = super
+ res.open("system-out").append(block)
+ return res
+ end
+
+ redef var xml_classname
+ redef var xml_name
end
redef class ModelBuilder
var prefix = toolcontext.test_dir
prefix = prefix.join_path(mmodule.to_s)
- var d2m = new NitUnitExecutor(toolcontext, prefix, o, ts)
-
- var tc
+ var d2m = new NitUnitExecutor(toolcontext, prefix, o, ts, "Docunits of module {mmodule.full_name}")
do
total_entities += 1
var ndoc = nmoduledecl.n_doc
if ndoc == null then break label x
doc_entities += 1
- tc = new HTMLTag("testcase")
# NOTE: jenkins expects a '.' in the classname attr
- tc.attr("classname", "nitunit." + mmodule.full_name + ".<module>")
- tc.attr("name", "<module>")
- d2m.extract(ndoc.to_mdoc, tc)
+ d2m.extract(ndoc.to_mdoc, "nitunit." + mmodule.full_name + ".<module>", "<module>")
end label x
for nclassdef in nmodule.n_classdefs do
var mclassdef = nclassdef.mclassdef
var ndoc = nclassdef.n_doc
if ndoc != null then
doc_entities += 1
- tc = new HTMLTag("testcase")
- tc.attr("classname", "nitunit." + mmodule.full_name + "." + mclassdef.mclass.full_name)
- tc.attr("name", "<class>")
- d2m.extract(ndoc.to_mdoc, tc)
+ d2m.extract(ndoc.to_mdoc, "nitunit." + mmodule.full_name + "." + mclassdef.mclass.full_name, "<class>")
end
end
for npropdef in nclassdef.n_propdefs do
var ndoc = npropdef.n_doc
if ndoc != null then
doc_entities += 1
- tc = new HTMLTag("testcase")
- tc.attr("classname", "nitunit." + mmodule.full_name + "." + mclassdef.mclass.full_name)
- tc.attr("name", mpropdef.mproperty.full_name)
- d2m.extract(ndoc.to_mdoc, tc)
+ d2m.extract(ndoc.to_mdoc, "nitunit." + mmodule.full_name + "." + mclassdef.mclass.full_name, mpropdef.mproperty.full_name)
end
end
end
var prefix = toolcontext.test_dir
prefix = prefix.join_path(mgroup.to_s)
- var d2m = new NitUnitExecutor(toolcontext, prefix, o, ts)
-
- var tc
+ var d2m = new NitUnitExecutor(toolcontext, prefix, o, ts, "Docunits of group {mgroup.full_name}")
total_entities += 1
var mdoc = mgroup.mdoc
if mdoc == null then return ts
doc_entities += 1
- tc = new HTMLTag("testcase")
# NOTE: jenkins expects a '.' in the classname attr
- tc.attr("classname", "nitunit." + mgroup.full_name)
- tc.attr("name", "<group>")
- d2m.extract(mdoc, tc)
+ d2m.extract(mdoc, "nitunit." + mgroup.full_name, "<group>")
d2m.run_tests
ts.attr("package", file)
var prefix = toolcontext.test_dir / "file"
- var d2m = new NitUnitExecutor(toolcontext, prefix, null, ts)
-
- var tc
+ var d2m = new NitUnitExecutor(toolcontext, prefix, null, ts, "Docunits of file {file}")
total_entities += 1
doc_entities += 1
- tc = new HTMLTag("testcase")
# NOTE: jenkins expects a '.' in the classname attr
- tc.attr("classname", "nitunit.<file>")
- tc.attr("name", file)
-
- d2m.extract(mdoc, tc)
+ d2m.extract(mdoc, "nitunit.<file>", file)
d2m.run_tests
return ts
# Test to be executed after the whole test suite.
var after_module: nullable TestCase = null
+ fun show_status(more_message: nullable String)
+ do
+ toolcontext.show_unit_status("Test-suite of module " + mmodule.full_name, test_cases, more_message)
+ end
+
# Execute the test suite
fun run do
+ show_status
if not toolcontext.test_dir.file_exists then
toolcontext.test_dir.mkdir
end
toolcontext.info("Execute test-suite {mmodule.name}", 1)
var before_module = self.before_module
if not before_module == null then before_module.run
- for case in test_cases do case.run
+ for case in test_cases do
+ case.run
+ show_status(case.full_name + " " + case.status_tag)
+ end
+
+ show_status
+ print ""
+
var after_module = self.after_module
if not after_module == null then after_module.run
+ for case in test_cases do
+ toolcontext.show_unit(case)
+ end
end
# Write the test unit for `self` in a nit compilable file.
# A test case is a unit test considering only a `MMethodDef`.
class TestCase
+ super UnitTest
# Test suite wich `self` belongs to.
var test_suite: TestSuite
# Test method to be compiled and tested.
var test_method: MMethodDef
+ redef fun full_name do return test_method.full_name
+
+ redef fun location do return test_method.location
+
# `ToolContext` to use to display messages and find `nitc` bin.
var toolcontext: ToolContext
var test_file = test_suite.test_file
var res_name = "{test_file}_{method_name.escape_to_c}"
var res = toolcontext.safe_exec("{test_file}.bin {method_name} > '{res_name}.out1' 2>&1 </dev/null")
- var f = new FileReader.open("{res_name}.out1")
- var msg = f.read_all
- f.close
+ self.raw_output = "{res_name}.out1".to_path.read_all
# set test case result
- var loc = test_method.location
if res != 0 then
- error = msg
- toolcontext.warning(loc, "failure",
- "ERROR: {method_name} (in file {test_file}.nit): {msg}")
+ error = "Runtime Error in file {test_file}.nit"
toolcontext.modelbuilder.failed_tests += 1
else
+ # no error, check with res file, if any.
var mmodule = test_method.mclassdef.mmodule
var file = mmodule.filepath
if file != null then
toolcontext.info("Diff output with {sav}", 1)
res = toolcontext.safe_exec("diff -u --label 'expected:{sav}' --label 'got:{res_name}.out1' '{sav}' '{res_name}.out1' > '{res_name}.diff' 2>&1 </dev/null")
if res != 0 then
- msg = "Diff\n" + "{res_name}.diff".to_path.read_all
- error = msg
- toolcontext.warning(loc, "failure",
- "ERROR: {method_name} (in file {test_file}.nit): {msg}")
+ self.raw_output = "Diff\n" + "{res_name}.diff".to_path.read_all
+ error = "Difference with expected output: diff -u {sav} {res_name}.out1"
toolcontext.modelbuilder.failed_tests += 1
end
else
end
end
end
- toolcontext.check_errors
+ is_done = true
end
- # Error occured during test-case execution.
- var error: nullable String = null
-
- # Was the test case executed at least one?
- var was_exec = false
-
- # Return the `TestCase` in XML format compatible with Jenkins.
- fun to_xml: HTMLTag do
+ redef fun xml_classname do
var mclassdef = test_method.mclassdef
- var tc = new HTMLTag("testcase")
- # NOTE: jenkins expects a '.' in the classname attr
- tc.attr("classname", "nitunit." + mclassdef.mmodule.full_name + "." + mclassdef.mclass.full_name)
- tc.attr("name", test_method.mproperty.full_name)
- if was_exec then
- tc.add new HTMLTag("system-out")
- var n = new HTMLTag("system-err")
- tc.add n
- var error = self.error
- if error != null then
- n.append error.trunc(8192).filter_nonprintable
- n = new HTMLTag("error")
- n.attr("message", "Runtime Error")
- tc.add n
- end
- end
- return tc
+ return "nitunit." + mclassdef.mmodule.full_name + "." + mclassdef.mclass.full_name
+ end
+
+ redef fun xml_name do
+ return test_method.mproperty.full_name
end
end
# Option --nit-dir
var opt_nit_dir = new OptionString("Base directory of the Nit installation", "--nit-dir")
+ # Option --share-dir
+ var opt_share_dir = new OptionString("Directory containing tools assets", "--share-dir")
+
# Option --help
var opt_help = new OptionBool("Show Help (This screen)", "-h", "-?", "--help")
# The identified root directory of the Nit package
var nit_dir: String is noinit
+ # Shared files directory.
+ #
+ # Most often `nit/share/`.
+ var share_dir: String is lazy do
+ var sharedir = opt_share_dir.value
+ if sharedir == null then
+ sharedir = nit_dir / "share"
+ if not sharedir.file_exists then
+ fatal_error(null, "Fatal Error: cannot locate shared files directory in {sharedir}. Uses --share-dir to define it's location.")
+ end
+ end
+ return sharedir
+ end
+
private fun compute_nit_dir: String
do
# the option has precedence
--- /dev/null
+# This file is part of NIT ( http://www.nitlanguage.org ).
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+
+module model_api
+
+import web_base
+import highlight
+import uml
+
+# Specific handler for nitweb API.
+abstract class APIHandler
+ super ModelHandler
+
+ # The JSON API does not filter anything by default.
+ #
+ # So we can cache the model view.
+ var view: ModelView is lazy do
+ var view = new ModelView(model)
+ view.min_visibility = private_visibility
+ view.include_fictive = true
+ view.include_empty_doc = true
+ view.include_attribute = true
+ view.include_test_suite = true
+ return view
+ end
+
+ # Try to load the mentity from uri with `/:id`.
+ #
+ # Send 400 if `:id` is null.
+ # Send 404 if no entity is found.
+ # Return null in both cases.
+ fun mentity_from_uri(req: HttpRequest, res: HttpResponse): nullable MEntity do
+ var id = req.param("id")
+ if id == null then
+ res.error 400
+ return null
+ end
+ var mentity = find_mentity(view, id)
+ if mentity == null then
+ res.error 404
+ end
+ return mentity
+ end
+end
+
+# Group all api handlers in one router.
+class APIRouter
+ super Router
+
+ # Model to pass to handlers.
+ var model: Model
+
+ # ModelBuilder to pass to handlers.
+ var modelbuilder: ModelBuilder
+
+ # Mainmodule to pass to handlers.
+ var mainmodule: MModule
+
+ init do
+ use("/list", new APIList(model, mainmodule))
+ use("/search", new APISearch(model, mainmodule))
+ use("/random", new APIRandom(model, mainmodule))
+ use("/entity/:id", new APIEntity(model, mainmodule))
+ use("/code/:id", new APIEntityCode(model, mainmodule, modelbuilder))
+ use("/uml/:id", new APIEntityUML(model, mainmodule))
+ end
+end
+
+# Search mentities from a query string.
+#
+# Example: `GET /search?q=Arr`
+class APISearch
+ super APIHandler
+
+ redef fun get(req, res) do
+ var q = req.string_arg("q")
+ if q == null then
+ res.error 400
+ return
+ end
+ var arr = new JsonArray
+ for mentity in view.mentities do
+ if mentity.name.has_prefix(q) then arr.add mentity
+ end
+ res.json arr
+ end
+end
+
+# List all mentities.
+#
+# MEntities can be filtered on their kind using the `k` parameter.
+# Allowed kinds are `package`, `group`, `module`, `class`, `classdef`, `property`, `propdef`.
+#
+# List size can be limited with the `n` parameter.
+#
+# Example: `GET /list?k=module?n=10`
+class APIList
+ super APIHandler
+
+ # List mentities depending on the `k` kind parameter.
+ fun list_mentities(req: HttpRequest): Array[MEntity] do
+ var k = req.string_arg("k")
+ var mentities = new Array[MEntity]
+ if k == "package" then
+ for mentity in view.mpackages do mentities.add mentity
+ else if k == "group" then
+ for mentity in view.mgroups do mentities.add mentity
+ else if k == "module" then
+ for mentity in view.mmodules do mentities.add mentity
+ else if k == "class" then
+ for mentity in view.mclasses do mentities.add mentity
+ else if k == "classdef" then
+ for mentity in view.mclassdefs do mentities.add mentity
+ else if k == "property" then
+ for mentity in view.mproperties do mentities.add mentity
+ else if k == "propdef" then
+ for mentity in view.mpropdefs do mentities.add mentity
+ else
+ for mentity in view.mentities do mentities.add mentity
+ end
+ return mentities
+ end
+
+ # Limit mentities depending on the `n` parameter.
+ fun limit_mentities(req: HttpRequest, mentities: Array[MEntity]): Array[MEntity] do
+ var n = req.int_arg("n")
+ if n != null then
+ return mentities.sub(0, n)
+ end
+ return mentities
+ end
+
+ redef fun get(req, res) do
+ var mentities = list_mentities(req)
+ mentities = limit_mentities(req, mentities)
+ var arr = new JsonArray
+ for mentity in mentities do arr.add mentity
+ res.json arr
+ end
+end
+
+# Return a random list of MEntities.
+#
+# Example: `GET /random?n=10&k=module`
+class APIRandom
+ super APIList
+
+ # Randomize mentities order.
+ fun randomize_mentities(req: HttpRequest, mentities: Array[MEntity]): Array[MEntity] do
+ var res = mentities.to_a
+ res.shuffle
+ return res
+ end
+
+ redef fun get(req, res) do
+ var mentities = list_mentities(req)
+ mentities = limit_mentities(req, mentities)
+ mentities = randomize_mentities(req, mentities)
+ var arr = new JsonArray
+ for mentity in mentities do arr.add mentity
+ res.json arr
+ end
+end
+
+# Return the JSON representation of a MEntity.
+#
+# Example: `GET /entity/core::Array`
+class APIEntity
+ super APIHandler
+
+ redef fun get(req, res) do
+ var mentity = mentity_from_uri(req, res)
+ if mentity == null then return
+ res.json mentity.api_json(self)
+ end
+end
+
+
+# Return a UML representation of MEntity.
+#
+# Example: `GET /entity/core::Array/uml`
+class APIEntityUML
+ super APIHandler
+
+ redef fun get(req, res) do
+ var mentity = mentity_from_uri(req, res)
+ var dot
+ if mentity isa MClassDef then mentity = mentity.mclass
+ if mentity isa MClass then
+ var uml = new UMLModel(view, mainmodule)
+ dot = uml.generate_class_uml.write_to_string
+ else if mentity isa MModule then
+ var uml = new UMLModel(view, mentity)
+ dot = uml.generate_package_uml.write_to_string
+ else
+ res.error 404
+ return
+ end
+ res.send render_svg(dot)
+ end
+
+ # Render a `dot` string as a svg image.
+ fun render_svg(dot: String): String do
+ var proc = new ProcessDuplex("dot", "-Tsvg")
+ var svg = proc.write_and_read(dot)
+ proc.close
+ proc.wait
+ return svg
+ end
+end
+
+# Return the source code of MEntity.
+#
+# Example: `GET /entity/core::Array/code`
+class APIEntityCode
+ super APIHandler
+
+ # Modelbuilder used to access sources.
+ var modelbuilder: ModelBuilder
+
+ redef fun get(req, res) do
+ var mentity = mentity_from_uri(req, res)
+ if mentity == null then return
+ var source = render_source(mentity)
+ if source == null then
+ res.error 404
+ return
+ end
+ res.send source
+ end
+
+ # Highlight `mentity` source code.
+ private fun render_source(mentity: MEntity): nullable HTMLTag do
+ var node = modelbuilder.mentity2node(mentity)
+ if node == null then return null
+ var hl = new HighlightVisitor
+ hl.enter_visit node
+ return hl.html
+ end
+end
module web
import web_actions
+import model_api
# Display the tree of all loaded mentities.
class TreeAction
- super ModelAction
+ super ModelHandler
redef fun get(req, res) do
var model = init_model_view(req)
end
end
-# Display the list of mentities matching `namespace`.
-class SearchAction
- super ModelAction
-
- # TODO handle more than full namespaces.
- redef fun get(req, res) do
- var namespace = req.param("namespace")
- var model = init_model_view(req)
- var mentity = find_mentity(model, namespace)
- if mentity == null then
- res.error(404)
- return
- end
- if req.is_json_asked then
- res.json(mentity.to_json)
- return
- end
- var view = new HtmlResultPage(namespace or else "null", [mentity])
- res.send_view(view)
- end
-end
-
-# Display a MEntity source code.
-class CodeAction
- super ModelAction
-
- # Modelbuilder used to access sources.
- var modelbuilder: ModelBuilder
-
- redef fun get(req, res) do
- var namespace = req.param("namespace")
- var model = init_model_view(req)
- var mentity = find_mentity(model, namespace)
- if mentity == null then
- res.error(404)
- return
- end
- var view = new HtmlSourcePage(modelbuilder, mentity)
- res.send_view(view)
- end
-end
-
# Display the doc of a MEntity.
class DocAction
- super ModelAction
+ super ModelHandler
# Modelbuilder used to access sources.
var modelbuilder: ModelBuilder
res.error(404)
return
end
- if req.is_json_asked then
- res.json(mentity.to_json)
- return
- end
-
var view = new HtmlDocPage(modelbuilder, mentity)
res.send_view(view)
end
end
-
-# Return an UML diagram for `namespace`.
-class UMLDiagramAction
- super ModelAction
-
- # Mainmodule used for hierarchy flattening.
- var mainmodule: MModule
-
- redef fun get(req, res) do
- var namespace = req.param("namespace")
- var model = init_model_view(req)
- var mentity = find_mentity(model, namespace)
- if mentity == null then
- res.error(404)
- return
- end
-
- var dot
- if mentity isa MClassDef then mentity = mentity.mclass
- if mentity isa MClass then
- var uml = new UMLModel(model, mainmodule)
- dot = uml.generate_class_uml.write_to_string
- else if mentity isa MModule then
- var uml = new UMLModel(model, mentity)
- dot = uml.generate_package_uml.write_to_string
- else
- res.error(404)
- return
- end
- var view = new HtmlDotPage(dot, mentity.as(not null).html_name)
- res.send_view(view)
- end
-end
-
-# Return a random list of MEntities.
-class RandomAction
- super ModelAction
-
- redef fun get(req, res) do
- var n = req.int_arg("n") or else 10
- var k = req.string_arg("k") or else "modules"
- var model = init_model_view(req)
- var mentities: Array[MEntity]
- if k == "modules" then
- mentities = model.mmodules.to_a
- else if k == "classdefs" then
- mentities = model.mclassdefs.to_a
- else
- mentities = model.mpropdefs.to_a
- end
- mentities.shuffle
- mentities = mentities.sub(0, n)
- if req.is_json_asked then
- var json = new JsonArray
- for mentity in mentities do
- json.add mentity.to_json
- end
- res.json(json)
- return
- end
- var view = new HtmlResultPage("random", mentities)
- res.send_view(view)
- end
-end
import model::model_views
import model::model_json
+import doc_down
import popcorn
# Specific nitcorn Action that uses a Model
-class ModelAction
+class ModelHandler
super Handler
# Model to use.
var model: Model
+ # MModule used to flatten model.
+ var mainmodule: MModule
+
# Find the MEntity ` with `full_name`.
fun find_mentity(model: ModelView, full_name: nullable String): nullable MEntity do
if full_name == null then return null
fun send_view(view: NitView, status: nullable Int) do send(view.render, status)
end
-redef class HttpRequest
- # Does the client asked for a json formatted response?
- #
- # Checks the URL get parameter `?json=true`.
- fun is_json_asked: Bool do return bool_arg("json") or else false
+redef class MEntity
+
+ # URL to `self` within the web interface.
+ fun web_url: String is abstract
+
+ # URL to `self` within the JSON api.
+ fun api_url: String do return "/api/entity/" / full_name
+
+ redef fun json do
+ var obj = super
+ obj["web_url"] = web_url
+ obj["api_url"] = api_url
+ return obj
+ end
+
+ # Get the full json repesentation of `self` with MEntityRefs resolved.
+ fun api_json(handler: ModelHandler): JsonObject do return json
+end
+
+redef class MEntityRef
+ redef fun json do
+ var obj = super
+ obj["web_url"] = mentity.web_url
+ obj["api_url"] = mentity.api_url
+ obj["name"] = mentity.name
+ obj["mdoc"] = mentity.mdoc_or_fallback
+ obj["visibility"] = mentity.visibility
+ obj["location"] = mentity.location
+ var modifiers = new JsonArray
+ for modifier in mentity.collect_modifiers do
+ modifiers.add modifier
+ end
+ obj["modifiers"] = modifiers
+ return obj
+ end
+end
+
+redef class MDoc
+
+ # Add doc down processing
+ redef fun json do
+ var obj = super
+ obj["synopsis"] = synopsis
+ obj["documentation"] = documentation
+ obj["comment"] = comment
+ obj["html_synopsis"] = html_synopsis.write_to_string
+ obj["html_documentation"] = html_documentation.write_to_string
+ obj["html_comment"] = html_comment.write_to_string
+ return obj
+ end
+end
+
+redef class MPackage
+ redef var web_url = "/package/{full_name}" is lazy
+end
+
+redef class MGroup
+ redef var web_url = "/group/{full_name}" is lazy
+end
+
+redef class MModule
+ redef var web_url = "/module/{full_name}" is lazy
+
+ redef fun api_json(handler) do
+ var obj = super
+ obj["intro_mclassdefs"] = to_mentity_refs(collect_intro_mclassdefs(private_view))
+ obj["redef_mclassdefs"] = to_mentity_refs(collect_redef_mclassdefs(private_view))
+ obj["imports"] = to_mentity_refs(in_importation.direct_greaters)
+ return obj
+ end
+end
+
+redef class MClass
+ redef var web_url = "/class/{full_name}" is lazy
+
+ redef fun api_json(handler) do
+ var obj = super
+ obj["all_mproperties"] = to_mentity_refs(collect_accessible_mproperties(private_view))
+ obj["intro_mproperties"] = to_mentity_refs(collect_intro_mproperties(private_view))
+ obj["redef_mproperties"] = to_mentity_refs(collect_redef_mproperties(private_view))
+ var poset = hierarchy_poset(handler.mainmodule, private_view)
+ obj["parents"] = to_mentity_refs(poset[self].direct_greaters)
+ return obj
+ end
+end
+
+redef class MClassDef
+ redef var web_url = "/classdef/{full_name}" is lazy
+
+ redef fun json do
+ var obj = super
+ obj["intro"] = to_mentity_ref(mclass.intro)
+ obj["mpackage"] = to_mentity_ref(mmodule.mpackage)
+ return obj
+ end
+
+ redef fun api_json(handler) do
+ var obj = super
+ obj["intro_mpropdefs"] = to_mentity_refs(collect_intro_mpropdefs(private_view))
+ obj["redef_mpropdefs"] = to_mentity_refs(collect_redef_mpropdefs(private_view))
+ return obj
+ end
+end
+
+redef class MProperty
+ redef var web_url = "/property/{full_name}" is lazy
+
+ redef fun json do
+ var obj = super
+ obj["intro_mclass"] = to_mentity_ref(intro_mclassdef.mclass)
+ obj["mpackage"] = to_mentity_ref(intro_mclassdef.mmodule.mpackage)
+ return obj
+ end
+end
+
+redef class MPropDef
+ redef var web_url = "/propdef/{full_name}" is lazy
+
+ redef fun json do
+ var obj = super
+ obj["intro"] = to_mentity_ref(mproperty.intro)
+ obj["intro_mclassdef"] = to_mentity_ref(mproperty.intro.mclassdef)
+ obj["mmodule"] = to_mentity_ref(mclassdef.mmodule)
+ obj["mgroup"] = to_mentity_ref(mclassdef.mmodule.mgroup)
+ obj["mpackage"] = to_mentity_ref(mclassdef.mmodule.mpackage)
+ return obj
+ end
+end
+
+redef class MClassType
+ redef var web_url = mclass.web_url is lazy
+end
+
+redef class MNullableType
+ redef var web_url = mtype.web_url is lazy
+end
+
+redef class MParameterType
+ redef var web_url = mclass.web_url is lazy
+end
+
+redef class MVirtualType
+ redef var web_url = mproperty.web_url is lazy
end
end
end
-# Display a search results list.
-class HtmlResultPage
- super NitView
-
- # Initial query.
- var query: String
-
- # Result set
- var results: Array[MEntity]
-
- redef fun render do
- var tpl = new Template
- tpl.add new Header(1, "Results for {query}")
- if results.is_empty then
- tpl.add "<p>No result for {query}.<p>"
- return tpl
- end
- var list = new UnorderedList
- for mentity in results do
- var link = mentity.html_link
- link.text = mentity.html_full_name
- list.add_li new ListItem(link)
- end
- tpl.add list
- return tpl
- end
-end
-
# Display the source for each mentities
class HtmlSourcePage
super NitView
return tpl
end
end
-
-# Display the source for each mentities
-class HtmlDotPage
- super NitView
-
- # Dot to process.
- var dot: Text
-
- # Page title.
- var title: String
-
- redef fun render do
- var tpl = new Template
- tpl.add new Header(1, title)
- tpl.add render_dot
- return tpl
- end
-
- private fun render_dot: String do
- var proc = new ProcessDuplex("dot", "-Tsvg", "-Tcmapx")
- var svg = proc.write_and_read(dot)
- proc.close
- proc.wait
- return svg
- end
-end
mpi
emscripten
ui_test
+readline
# This file is part of NIT ( http://www.nitlanguage.org ).
#
-# Copyright 2012 Alexis Laferrière <alexis.laf@xymus.net>
-#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
# See the License for the specific language governing permissions and
# limitations under the License.
-import realtime
+import end
-redef extern class Timespec
- fun simplify : Int
- do
- return sec*1000000 + nanosec/1000
- end
+interface Object
+ type SELF: Object
+ fun output_class_name is intern
end
-var c = new Clock
-var t0 = c.total.simplify
-
-print "sleeping 1s"
-nanosleep(1, 0)
-print c.total.sec >= 1
-print c.lapse.sec >= 1
-
-var t1 = c.total.simplify
+class A[E]
+ new do return new B[E]
+end
-print "sleeping 5000ns"
-nanosleep(0, 5000)
-print c.lapse.nanosec >= 5000
+class B[E]
+ super A[E]
-var t2 = c.total.simplify
+ fun foo: A[E] do return new A[SELF]
+end
-print t0 <= t1
-print t1 <= t2
+(new B[Object]).foo.output_class_name
../examples/*/src/*_android.nit \
../examples/*/src/*_linux.nit \
../examples/*/src/*_null.nit \
- ../examples/nitcorn/src/*.nit \
../lib/*/examples/*.nit \
../lib/*/examples/*/*.nit \
../contrib/friendz/src/solver_cmd.nit \
test_rubix_cube
test_rubix_visual
test_csv
+repeating_key_xor_solve
test_nitunit.nit --no-color -o $WRITE
test_nitunit.nit --gen-suite --only-show
test_nitunit.nit --gen-suite --only-show --private
-test_nitunit2.nit -o $WRITE
+test_nitunit2.nit --no-color -o $WRITE
test_doc2.nit --no-color -o $WRITE
test_nitunit3 --no-color -o $WRITE
test_nitunit_md.md --no-color -o $WRITE
test_rubix_visual
test_rubix_cube
test_csv
+repeating_key_xor_solve
--- /dev/null
+../lib/crapto/examples/repeating_key_xor_cipher.txt
--- /dev/null
+B[B[Object]]
<h3>Quality</h3>
<ul class="box">
<li>28 warnings (63/kloc)</li>
-<li>93% documented</li>
+<li>95% documented</li>
</ul>
<h3>Tags</h3>
<a href="../index.html#tag_test">test</a>, <a href="../index.html#tag_game">game</a><h3>Requirements</h3>
--- /dev/null
+Fatal Error: limitation in the rapidtype analysis engine: a type depth of 256 is too important, the problematic type is `A[A[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[Sys]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]`.
--- /dev/null
+Fatal Error: limitation in the rapidtype analysis engine: a type depth of 256 is too important, the problematic type is `A[A[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[Sys]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]`.
--- /dev/null
+Fatal Error: limitation in the rapidtype analysis engine: a type depth of 256 is too important, the problematic type is `A[A[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[B[Sys]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]]`.
-test_nitunit.nit:20,1--22,0: ERROR: nitunit.test_nitunit::test_nitunit.test_nitunit::X.<class> (in .nitunit/test_nitunit-2.nit):
-Runtime error: Assert failed (.nitunit/test_nitunit-2.nit:5)
+* Docunits of module test_nitunit::test_nitunit (4 tests)
-test_nitunit.nit:23,2--25,0: FAILURE: nitunit.test_nitunit::test_nitunit.test_nitunit::X.test_nitunit::X::foo (in .nitunit/test_nitunit-3.nit):
-.nitunit/test_nitunit-3.nit:5,8--27: Error: method or variable `undefined_identifier` unknown in `Sys`.
+[OK] test_nitunit::test_nitunit
+[KO] test_nitunit$X
+ test_nitunit.nit:21,7--22,0: Runtime error in nitunit.out/test_nitunit-2.nit
+ Output
+ Runtime error: Assert failed (nitunit.out/test_nitunit-2.nit:5)
-test_test_nitunit.nit:36,2--40,4: ERROR: test_foo1 (in file .nitunit/gen_test_test_nitunit.nit): Runtime error: Assert failed (test_test_nitunit.nit:39)
+[KO] test_nitunit$X$foo
+ test_nitunit.nit:24,8--25,0: Compilation error in nitunit.out/test_nitunit-3.nit
+ Output
+ nitunit.out/test_nitunit-3.nit:5,8--27: Error: method or variable `undefined_identifier` unknown in `Sys`.
-DocUnits:
-Entities: 27; Documented ones: 3; With nitunits: 3; Failures: 2
+[KO] test_nitunit$X$foo1
+ test_nitunit.nit:28,15: Syntax Error: unexpected operator '!'.
+* Test-suite of module test_test_nitunit::test_test_nitunit (3 tests)
-TestSuites:
-Class suites: 1; Test Cases: 3; Failures: 1
+[OK] test_test_nitunit$TestX$test_foo
+[KO] test_test_nitunit$TestX$test_foo1
+ test_test_nitunit.nit:36,2--40,4: Runtime Error in file nitunit.out/gen_test_test_nitunit.nit
+ Output
+ Runtime error: Assert failed (test_test_nitunit.nit:39)
+
+[OK] test_test_nitunit$TestX$test_foo2
+Docunits: Entities: 27; Documented ones: 4; With nitunits: 4; Failures: 3
+Test suites: Classes: 1; Test Cases: 3; Failures: 1
+[FAILURE] 4/7 tests failed.
+`nitunit.out` is not removed for investigation.
<testsuites><testsuite package="test_nitunit::test_nitunit"><testcase classname="nitunit.test_nitunit::test_nitunit.<module>" name="<module>"><system-err></system-err><system-out>assert true
-</system-out></testcase><testcase classname="nitunit.test_nitunit::test_nitunit.test_nitunit::X" name="<class>"><system-err>Runtime error: Assert failed (.nitunit/test_nitunit-2.nit:5)
+</system-out></testcase><testcase classname="nitunit.test_nitunit::test_nitunit.test_nitunit::X" name="<class>"><error>Runtime error in nitunit.out/test_nitunit-2.nit</error><system-err>Runtime error: Assert failed (nitunit.out/test_nitunit-2.nit:5)
</system-err><system-out>assert false
-</system-out><error message="Runtime Error"></error></testcase><testcase classname="nitunit.test_nitunit::test_nitunit.test_nitunit::X" name="test_nitunit::X::foo"><system-err>.nitunit/test_nitunit-3.nit:5,8--27: Error: method or variable `undefined_identifier` unknown in `Sys`.
+</system-out></testcase><testcase classname="nitunit.test_nitunit::test_nitunit.test_nitunit::X" name="test_nitunit::X::foo"><failure>Compilation error in nitunit.out/test_nitunit-3.nit</failure><system-err>nitunit.out/test_nitunit-3.nit:5,8--27: Error: method or variable `undefined_identifier` unknown in `Sys`.
</system-err><system-out>assert undefined_identifier
-</system-out><failure message="Compilation Error"></failure></testcase></testsuite><testsuite package="test_test_nitunit"><testcase classname="nitunit.test_test_nitunit::test_test_nitunit.test_test_nitunit::TestX" name="test_test_nitunit::TestX::test_foo"><system-out></system-out><system-err></system-err></testcase><testcase classname="nitunit.test_test_nitunit::test_test_nitunit.test_test_nitunit::TestX" name="test_test_nitunit::TestX::test_foo1"><system-out></system-out><system-err>Runtime error: Assert failed (test_test_nitunit.nit:39)
-</system-err><error message="Runtime Error"></error></testcase><testcase classname="nitunit.test_test_nitunit::test_test_nitunit.test_test_nitunit::TestX" name="test_test_nitunit::TestX::test_foo2"><system-out></system-out><system-err></system-err></testcase></testsuite></testsuites>
\ No newline at end of file
+</system-out></testcase><testcase classname="nitunit.test_nitunit::test_nitunit.test_nitunit::X" name="test_nitunit::X::foo1"><failure>Syntax Error: unexpected operator '!'.</failure><system-out>assert !@#$%^&*()
+</system-out></testcase></testsuite><testsuite package="test_test_nitunit"><testcase classname="nitunit.test_test_nitunit::test_test_nitunit.test_test_nitunit::TestX" name="test_test_nitunit::TestX::test_foo"><system-err></system-err></testcase><testcase classname="nitunit.test_test_nitunit::test_test_nitunit.test_test_nitunit::TestX" name="test_test_nitunit::TestX::test_foo1"><error>Runtime Error in file nitunit.out/gen_test_test_nitunit.nit</error><system-err>Runtime error: Assert failed (test_test_nitunit.nit:39)
+</system-err></testcase><testcase classname="nitunit.test_test_nitunit::test_test_nitunit.test_test_nitunit::TestX" name="test_test_nitunit::TestX::test_foo2"><system-err></system-err></testcase></testsuite></testsuites>
\ No newline at end of file
-DocUnits:
-DocUnits Success
-Entities: 4; Documented ones: 3; With nitunits: 3; Failures: 0
+* Docunits of module test_nitunit2::test_nitunit2 (3 tests)
-TestSuites:
-No test cases found
-Class suites: 0; Test Cases: 0; Failures: 0
+[OK] test_nitunit2::test_nitunit2$core::Sys$foo1
+[OK] test_nitunit2::test_nitunit2$core::Sys$bar2
+[OK] test_nitunit2::test_nitunit2$core::Sys$foo3
+Docunits: Entities: 4; Documented ones: 3; With nitunits: 3; Failures: 0
+Test suites: Classes: 0; Test Cases: 0
+[SUCCESS] All 3 tests passed.
<testsuites><testsuite package="test_nitunit2::test_nitunit2"><testcase classname="nitunit.test_nitunit2::test_nitunit2.core::Sys" name="test_nitunit2::test_nitunit2::Sys::foo1"><system-err></system-err><system-out>if true then
assert true
-DocUnits:
-DocUnits Success
-Entities: 6; Documented ones: 5; With nitunits: 3; Failures: 0
+* Docunits of module test_doc2::test_doc2 (3 tests)
-TestSuites:
-No test cases found
-Class suites: 0; Test Cases: 0; Failures: 0
+[OK] test_doc2::test_doc2$core::Sys$foo1
+[OK] test_doc2::test_doc2$core::Sys$foo2
+[OK] test_doc2::test_doc2$core::Sys$foo3
+Docunits: Entities: 6; Documented ones: 5; With nitunits: 3; Failures: 0
+Test suites: Classes: 0; Test Cases: 0
+[SUCCESS] All 3 tests passed.
<testsuites><testsuite package="test_doc2::test_doc2"><testcase classname="nitunit.test_doc2::test_doc2.core::Sys" name="test_doc2::test_doc2::Sys::foo1"><system-err></system-err><system-out>assert true # tested
</system-out></testcase><testcase classname="nitunit.test_doc2::test_doc2.core::Sys" name="test_doc2::test_doc2::Sys::foo2"><system-err></system-err><system-out>assert true # tested
</system-out></testcase><testcase classname="nitunit.test_doc2::test_doc2.core::Sys" name="test_doc2::test_doc2::Sys::foo3"><system-err></system-err><system-out>assert true # tested
-test_nitunit3/README.md:7,3--5: Syntax Error: unexpected malformed character '\]. To suppress this message, enclose the block with a fence tagged `nitish` or `raw` (see `man nitdoc`).
-test_nitunit3/README.md:1,0--13,0: ERROR: nitunit.test_nitunit3>.<group> (in .nitunit/test_nitunit3-0.nit): Runtime error
-Runtime error: Assert failed (.nitunit/test_nitunit3-0.nit:7)
+* Docunits of group test_nitunit3> (2 tests)
-DocUnits:
-Entities: 2; Documented ones: 2; With nitunits: 3; Failures: 2
+[KO] test_nitunit3>
+ test_nitunit3/README.md:4,2--15,0: Runtime error in nitunit.out/test_nitunit3-0.nit with argument 1
+ Output
+ Runtime error: Assert failed (nitunit.out/test_nitunit3-0.nit:7)
-TestSuites:
-No test cases found
-Class suites: 0; Test Cases: 0; Failures: 0
-<testsuites><testsuite package="test_nitunit3>"><testcase classname="nitunit.test_nitunit3>" name="<group>"><failure message="test_nitunit3/README.md:7,3--5: Syntax Error: unexpected malformed character '\]."></failure><system-err>Runtime error: Assert failed (.nitunit/test_nitunit3-0.nit:7)
+[KO] test_nitunit3>
+ test_nitunit3/README.md:7,3--5: Syntax Error: unexpected malformed character '\].
+* Docunits of module test_nitunit3::test_nitunit3 (1 tests)
+
+[OK] test_nitunit3::test_nitunit3
+Docunits: Entities: 2; Documented ones: 2; With nitunits: 3; Failures: 2
+Test suites: Classes: 0; Test Cases: 0
+[FAILURE] 2/3 tests failed.
+`nitunit.out` is not removed for investigation.
+<testsuites><testsuite package="test_nitunit3>"><testcase classname="nitunit.test_nitunit3>" name="<group>"><error>Runtime error in nitunit.out/test_nitunit3-0.nit with argument 1</error><system-err>Runtime error: Assert failed (nitunit.out/test_nitunit3-0.nit:7)
</system-err><system-out>assert false
assert true
-</system-out><error message="Runtime error"></error></testcase></testsuite><testsuite package="test_nitunit3::test_nitunit3"><testcase classname="nitunit.test_nitunit3::test_nitunit3.<module>" name="<module>"><system-err></system-err><system-out>assert true
+</system-out></testcase><testcase classname="nitunit.test_nitunit3>" name="<group>+1"><failure>Syntax Error: unexpected malformed character '\].</failure><system-out>;'\][]
+</system-out></testcase></testsuite><testsuite package="test_nitunit3::test_nitunit3"><testcase classname="nitunit.test_nitunit3::test_nitunit3.<module>" name="<module>"><system-err></system-err><system-out>assert true
</system-out></testcase></testsuite><testsuite></testsuite></testsuites>
\ No newline at end of file
-test_nitunit_md.md:1,0--15,0: ERROR: nitunit.<file>.test_nitunit_md.md:1,0--15,0 (in .nitunit/file-0.nit): Runtime error
-Runtime error: Assert failed (.nitunit/file-0.nit:8)
+* Docunits of file test_nitunit_md.md:1,0--15,0 (1 tests)
-DocUnits:
-Entities: 1; Documented ones: 1; With nitunits: 1; Failures: 1
+[KO] nitunit.<file>.test_nitunit_md.md:1,0--15,0
+ test_nitunit_md.md:4,2--16,0: Runtime error in nitunit.out/file-0.nit with argument 1
+ Output
+ Runtime error: Assert failed (nitunit.out/file-0.nit:8)
-TestSuites:
-No test cases found
-Class suites: 0; Test Cases: 0; Failures: 0
-<testsuites><testsuite package="test_nitunit_md.md:1,0--15,0"><testcase classname="nitunit.<file>" name="test_nitunit_md.md:1,0--15,0"><system-err>Runtime error: Assert failed (.nitunit/file-0.nit:8)
+Docunits: Entities: 1; Documented ones: 1; With nitunits: 1; Failures: 1
+Test suites: Classes: 0; Test Cases: 0
+[FAILURE] 1/1 tests failed.
+`nitunit.out` is not removed for investigation.
+<testsuites><testsuite package="test_nitunit_md.md:1,0--15,0"><testcase classname="nitunit.<file>" name="test_nitunit_md.md:1,0--15,0"><error>Runtime error in nitunit.out/file-0.nit with argument 1</error><system-err>Runtime error: Assert failed (nitunit.out/file-0.nit:8)
</system-err><system-out>var a = 1
assert 1 == 1
assert false
-</system-out><error message="Runtime error"></error></testcase></testsuite></testsuites>
\ No newline at end of file
+</system-out></testcase></testsuite></testsuites>
\ No newline at end of file
-test_doc3.nit:17,9--15: Syntax Error: unexpected identifier 'garbage'. To suppress this message, enclose the block with a fence tagged `nitish` or `raw` (see `man nitdoc`).
-test_doc3.nit:23,4--10: Syntax Error: unexpected identifier 'garbage'. To suppress this message, enclose the block with a fence tagged `nitish` or `raw` (see `man nitdoc`).
-test_doc3.nit:30,4--10: Syntax Error: unexpected identifier 'garbage'. To suppress this message, enclose the block with a fence tagged `nitish` or `raw` (see `man nitdoc`).
-DocUnits:
-Entities: 6; Documented ones: 5; With nitunits: 3; Failures: 3
+* Docunits of module test_doc3::test_doc3 (3 tests)
-TestSuites:
-No test cases found
-Class suites: 0; Test Cases: 0; Failures: 0
-<testsuites><testsuite package="test_doc3::test_doc3"><testcase classname="nitunit.test_doc3::test_doc3.core::Sys" name="test_doc3::test_doc3::Sys::foo1"><failure message="test_doc3.nit:17,9--15: Syntax Error: unexpected identifier 'garbage'."></failure></testcase><testcase classname="nitunit.test_doc3::test_doc3.core::Sys" name="test_doc3::test_doc3::Sys::foo2"><failure message="test_doc3.nit:23,4--10: Syntax Error: unexpected identifier 'garbage'."></failure></testcase><testcase classname="nitunit.test_doc3::test_doc3.core::Sys" name="test_doc3::test_doc3::Sys::foo3"><failure message="test_doc3.nit:30,4--10: Syntax Error: unexpected identifier 'garbage'."></failure></testcase></testsuite><testsuite></testsuite></testsuites>
\ No newline at end of file
+[KO] test_doc3::test_doc3$core::Sys$foo1
+ test_doc3.nit:17,9--15: Syntax Error: unexpected identifier 'garbage'.
+[KO] test_doc3::test_doc3$core::Sys$foo2
+ test_doc3.nit:23,4--10: Syntax Error: unexpected identifier 'garbage'.
+[KO] test_doc3::test_doc3$core::Sys$foo3
+ test_doc3.nit:30,4--10: Syntax Error: unexpected identifier 'garbage'.
+Docunits: Entities: 6; Documented ones: 5; With nitunits: 3; Failures: 3
+Test suites: Classes: 0; Test Cases: 0
+[FAILURE] 3/3 tests failed.
+`nitunit.out` is not removed for investigation.
+<testsuites><testsuite package="test_doc3::test_doc3"><testcase classname="nitunit.test_doc3::test_doc3.core::Sys" name="test_doc3::test_doc3::Sys::foo1"><failure>Syntax Error: unexpected identifier 'garbage'.</failure><system-out> *garbage*
+</system-out></testcase><testcase classname="nitunit.test_doc3::test_doc3.core::Sys" name="test_doc3::test_doc3::Sys::foo2"><failure>Syntax Error: unexpected identifier 'garbage'.</failure><system-out>*garbage*
+</system-out></testcase><testcase classname="nitunit.test_doc3::test_doc3.core::Sys" name="test_doc3::test_doc3::Sys::foo3"><failure>Syntax Error: unexpected identifier 'garbage'.</failure><system-out>*garbage*
+</system-out></testcase></testsuite><testsuite></testsuite></testsuites>
\ No newline at end of file
-test_nitunit4/test_nitunit4.nit:22,2--26,4: ERROR: test_foo (in file .nitunit/gen_test_nitunit4.nit): Before Test
-Tested method
-After Test
-Runtime error: Assert failed (test_nitunit4/test_nitunit4_base.nit:31)
+* Test-suite of module test_nitunit4::test_nitunit4 (3 tests)
-test_nitunit4/test_nitunit4.nit:32,2--34,4: ERROR: test_baz (in file .nitunit/gen_test_nitunit4.nit): Diff
---- expected:test_nitunit4/test_nitunit4.sav/test_baz.res
-+++ got:.nitunit/gen_test_nitunit4_test_baz.out1
-@@ -1 +1,3 @@
--Bad result file
-+Before Test
-+Tested method
-+After Test
+[KO] test_nitunit4$TestTestSuite$test_foo
+ test_nitunit4/test_nitunit4.nit:22,2--26,4: Runtime Error in file nitunit.out/gen_test_nitunit4.nit
+ Output
+ Before Test
+ Tested method
+ After Test
+ Runtime error: Assert failed (test_nitunit4/test_nitunit4_base.nit:31)
-DocUnits:
-No doc units found
-Entities: 12; Documented ones: 0; With nitunits: 0; Failures: 0
+[OK] test_nitunit4$TestTestSuite$test_bar
+[KO] test_nitunit4$TestTestSuite$test_baz
+ test_nitunit4/test_nitunit4.nit:32,2--34,4: Difference with expected output: diff -u test_nitunit4/test_nitunit4.sav/test_baz.res nitunit.out/gen_test_nitunit4_test_baz.out1
+ Output
+ Diff
+ --- expected:test_nitunit4/test_nitunit4.sav/test_baz.res
+ +++ got:nitunit.out/gen_test_nitunit4_test_baz.out1
+ @@ -1 +1,3 @@
+ -Bad result file
+ +Before Test
+ +Tested method
+ +After Test
-TestSuites:
-Class suites: 1; Test Cases: 3; Failures: 2
-<testsuites><testsuite package="test_nitunit4>"></testsuite><testsuite package="test_nitunit4::nitunit4"></testsuite><testsuite package="test_nitunit4"><testcase classname="nitunit.test_nitunit4::test_nitunit4.test_nitunit4::TestTestSuite" name="test_nitunit4::TestTestSuite::test_foo"><system-out></system-out><system-err>Before Test
+Docunits: Entities: 12; Documented ones: 0; With nitunits: 0
+Test suites: Classes: 1; Test Cases: 3; Failures: 2
+[FAILURE] 2/3 tests failed.
+`nitunit.out` is not removed for investigation.
+<testsuites><testsuite package="test_nitunit4>"></testsuite><testsuite package="test_nitunit4::nitunit4"></testsuite><testsuite package="test_nitunit4"><testcase classname="nitunit.test_nitunit4::test_nitunit4.test_nitunit4::TestTestSuite" name="test_nitunit4::TestTestSuite::test_foo"><error>Runtime Error in file nitunit.out/gen_test_nitunit4.nit</error><system-err>Before Test
Tested method
After Test
Runtime error: Assert failed (test_nitunit4/test_nitunit4_base.nit:31)
-</system-err><error message="Runtime Error"></error></testcase><testcase classname="nitunit.test_nitunit4::test_nitunit4.test_nitunit4::TestTestSuite" name="test_nitunit4::TestTestSuite::test_bar"><system-out></system-out><system-err></system-err></testcase><testcase classname="nitunit.test_nitunit4::test_nitunit4.test_nitunit4::TestTestSuite" name="test_nitunit4::TestTestSuite::test_baz"><system-out></system-out><system-err>Diff
+</system-err></testcase><testcase classname="nitunit.test_nitunit4::test_nitunit4.test_nitunit4::TestTestSuite" name="test_nitunit4::TestTestSuite::test_bar"><system-err>Before Test
+Tested method
+After Test
+</system-err></testcase><testcase classname="nitunit.test_nitunit4::test_nitunit4.test_nitunit4::TestTestSuite" name="test_nitunit4::TestTestSuite::test_baz"><error>Difference with expected output: diff -u test_nitunit4/test_nitunit4.sav/test_baz.res nitunit.out/gen_test_nitunit4_test_baz.out1</error><system-err>Diff
--- expected:test_nitunit4/test_nitunit4.sav/test_baz.res
-+++ got:.nitunit/gen_test_nitunit4_test_baz.out1
++++ got:nitunit.out/gen_test_nitunit4_test_baz.out1
@@ -1 +1,3 @@
-Bad result file
+Before Test
+Tested method
+After Test
-</system-err><error message="Runtime Error"></error></testcase></testsuite><testsuite package="test_nitunit4::test_nitunit4"></testsuite><testsuite></testsuite><testsuite package="test_nitunit4::test_nitunit4_base"></testsuite><testsuite></testsuite></testsuites>
\ No newline at end of file
+</system-err></testcase></testsuite><testsuite package="test_nitunit4::test_nitunit4"></testsuite><testsuite></testsuite><testsuite package="test_nitunit4::test_nitunit4_base"></testsuite><testsuite></testsuite></testsuites>
\ No newline at end of file
--- /dev/null
+Usage: repeating_key_xor_solve <cipher_file>
--- /dev/null
+I'm back and I'm ringin' the bell
+A rockin' on the mike while the fly girls yell
+In ecstasy in the back of me
+Well that's my DJ Deshay cuttin' all them Z's
+Hittin' hard and the girlies goin' crazy
+Vanilla's on the mike, man I'm not lazy.
+
+I'm lettin' my drug kick in
+It controls my mouth and I begin
+To just let it flow, let my concepts go
+My posse's to the side yellin', Go Vanilla Go!
+
+Smooth 'cause that's the way I will be
+And if you don't give a damn, then
+Why you starin' at me
+So get off 'cause I control the stage
+There's no dissin' allowed
+I'm in my own phase
+The girlies sa y they love me and that is ok
+And I can dance better than any kid n' play
+
+Stage 2 -- Yea the one ya' wanna listen to
+It's off my head so let the beat play through
+So I can funk it up and make it sound good
+1-2-3 Yo -- Knock on some wood
+For good luck, I like my rhymes atrocious
+Supercalafragilisticexpialidocious
+I'm an effect and that you can bet
+I can take a fly girl and make her wet.
+
+I'm like Samson -- Samson to Delilah
+There's no denyin', You can try to hang
+But you'll keep tryin' to get my style
+Over and over, practice makes perfect
+But not if you're a loafer.
+
+You'll get nowhere, no place, no time, no girls
+Soon -- Oh my God, homebody, you probably eat
+Spaghetti with a spoon! Come on and say it!
+
+VIP. Vanilla Ice yep, yep, I'm comin' hard like a rhino
+Intoxicating so you stagger like a wino
+So punks stop trying and girl stop cryin'
+Vanilla Ice is sellin' and you people are buyin'
+'Cause why the freaks are jockin' like Crazy Glue
+Movin' and groovin' trying to sing along
+All through the ghetto groovin' this here song
+Now you're amazed by the VIP posse.
+
+Steppin' so hard like a German Nazi
+Startled by the bases hittin' ground
+There's no trippin' on mine, I'm just gettin' down
+Sparkamatic, I'm hangin' tight like a fanatic
+You trapped me once and I thought that
+You might have it
+So step down and lend me your ear
+'89 in my time! You, '90 is my year.
+
+You're weakenin' fast, YO! and I can tell it
+Your body's gettin' hot, so, so I can smell it
+So don't be mad and don't be sad
+'Cause the lyrics belong to ICE, You can call me Dad
+You're pitchin' a fit, so step back and endure
+Let the witch doctor, Ice, do the dance to cure
+So come up close and don't be square
+You wanna battle me -- Anytime, anywhere
+
+You thought that I was weak, Boy, you're dead wrong
+So come on, everybody and sing this song
+
+Say -- Play that funky music Say, go white boy, go white boy go
+play that funky music Go white boy, go white boy, go
+Lay down and boogie and play that funky music till you die.
+
+Play that funky music Come on, Come on, let me hear
+Play that funky music white boy you say it, say it
+Play that funky music A little louder now
+Play that funky music, white boy Come on, Come on, Come on
+Play that funky music
+
names::n3$::n1::P1$A::a MMethodDef names/n3.nit:31,2--32,19 a refinement (3 distinct modules)
names::n3$::n1::P1$::n0::P::p MMethodDef names/n3.nit:33,2--34,19 a refinement (3 distinct modules)
names::n0 MModule names/n0.nit:15,1--67,3 Root module
-names::Object MClass names/n0.nit:20,1--22,3
+names::Object MClass names/n0.nit:20,1--22,3 Root interface
names$Object MClassDef names/n0.nit:20,1--22,3 Root interface
names::Object::init MMethod names/n0.nit:20,1--22,3
names$Object$init MMethodDef names/n0.nit:20,1--22,3
-names::A MClass names/n0.nit:24,1--31,3
+names::A MClass names/n0.nit:24,1--31,3 A public class
names$A MClassDef names/n0.nit:24,1--31,3 A public class
-names::A::a MMethod names/n0.nit:26,2--27,13
+names::A::a MMethod names/n0.nit:26,2--27,13 A public method in a public class
names$A$a MMethodDef names/n0.nit:26,2--27,13 A public method in a public class
-names::n0::A::z MMethod names/n0.nit:29,2--30,21
+names::n0::A::z MMethod names/n0.nit:29,2--30,21 A private method in a public class
names$A$z MMethodDef names/n0.nit:29,2--30,21 A private method in a public class
-names::A0 MClass names/n0.nit:33,1--46,3
+names::A0 MClass names/n0.nit:33,1--46,3 A public subclass in the same module
names$A0 MClassDef names/n0.nit:33,1--46,3 A public subclass in the same module
names$A0$A::a MMethodDef names/n0.nit:38,2--39,19 Redefinition it the same module of a public method
names$A0$::n0::A::z MMethodDef names/n0.nit:41,2--42,19 Redefinition it the same module of a private method
names$A0$::n0::P::p MMethodDef names/n0.nit:44,2--45,19 Redefinition it the same module of a private method
-names::n0::P MClass names/n0.nit:48,1--52,3
+names::n0::P MClass names/n0.nit:48,1--52,3 A private class
names::n0$P MClassDef names/n0.nit:48,1--52,3 A private class
-names::n0::P::p MMethod names/n0.nit:50,2--51,13
+names::n0::P::p MMethod names/n0.nit:50,2--51,13 A private method in a private class
names::n0$P$p MMethodDef names/n0.nit:50,2--51,13 A private method in a private class
-names::n0::P0 MClass names/n0.nit:54,1--67,3
+names::n0::P0 MClass names/n0.nit:54,1--67,3 A private subclass introduced in the same module
names::n0$P0 MClassDef names/n0.nit:54,1--67,3 A private subclass introduced in the same module
names::n0$P0$A::a MMethodDef names/n0.nit:59,2--60,19 Redefinition it the same module of a public method
names::n0$P0$::n0::A::z MMethodDef names/n0.nit:62,2--63,19 Redefinition it the same module of a private method
names::n1$A MClassDef names/n1.nit:20,1--30,3 A refinement of a class
names::n1$A$a MMethodDef names/n1.nit:22,2--23,19 A refinement in the same class
names::n1$A$z MMethodDef names/n1.nit:25,2--26,19 A refinement in the same class
-names::n1::A::b MMethod names/n1.nit:28,2--29,13
+names::n1::A::b MMethod names/n1.nit:28,2--29,13 A public method introduced in a refinement
names::n1$A$b MMethodDef names/n1.nit:28,2--29,13 A public method introduced in a refinement
names::n1$A0 MClassDef names/n1.nit:32,1--42,3 A refinement of a subclass
names::n1$A0$A::a MMethodDef names/n1.nit:34,2--35,19 A refinement+redefinition
names::n1$A0$::n0::A::z MMethodDef names/n1.nit:37,2--38,19 A refinement+redefinition
names::n1$A0$::n0::P::p MMethodDef names/n1.nit:40,2--41,19 A refinement+redefinition
-names::A1 MClass names/n1.nit:44,1--57,3
+names::A1 MClass names/n1.nit:44,1--57,3 A subclass introduced in a submodule
names$A1 MClassDef names/n1.nit:44,1--57,3 A subclass introduced in a submodule
names$A1$A::a MMethodDef names/n1.nit:49,2--50,19 A redefinition in a subclass from a different module
names$A1$::n0::A::z MMethodDef names/n1.nit:52,2--53,19 A redefinition in a subclass from a different module
names::n1$::n0::P0$A::a MMethodDef names/n1.nit:67,2--68,19 A refinement+redefinition
names::n1$::n0::P0$::n0::A::z MMethodDef names/n1.nit:70,2--71,19 A refinement+redefinition
names::n1$::n0::P0$::n0::P::p MMethodDef names/n1.nit:73,2--74,19 A refinement+redefinition
-names::n1::P1 MClass names/n1.nit:77,1--90,3
+names::n1::P1 MClass names/n1.nit:77,1--90,3 A private subclass introduced in a different module
names::n1$P1 MClassDef names/n1.nit:77,1--90,3 A private subclass introduced in a different module
names::n1$P1$A::a MMethodDef names/n1.nit:82,2--83,19 A redefinition in a subclass from a different module
names::n1$P1$::n0::A::z MMethodDef names/n1.nit:85,2--86,19 A redefinition in a subclass from a different module
names::n1$P1$::n0::P::p MMethodDef names/n1.nit:88,2--89,19 A redefinition in a subclass from a different module
names::n2 MModule names/n2.nit:15,1--33,3 A alternative second module, used to make name conflicts
names::n2$A MClassDef names/n2.nit:20,1--27,3 A refinement of a class
-names::n2::A::b MMethod names/n2.nit:22,2--23,13
+names::n2::A::b MMethod names/n2.nit:22,2--23,13 Name conflict? A second public method
names::n2$A$b MMethodDef names/n2.nit:22,2--23,13 Name conflict? A second public method
-names::n2::A::z MMethod names/n2.nit:25,2--26,13
+names::n2::A::z MMethod names/n2.nit:25,2--26,13 Name conflict? A second private method
names::n2$A$z MMethodDef names/n2.nit:25,2--26,13 Name conflict? A second private method
-names::n2::P MClass names/n2.nit:29,1--33,3
+names::n2::P MClass names/n2.nit:29,1--33,3 Name conflict? A second private class
names::n2$P MClassDef names/n2.nit:29,1--33,3 Name conflict? A second private class
-names::n2::P::p MMethod names/n2.nit:31,2--32,13
+names::n2::P::p MMethod names/n2.nit:31,2--32,13 Name conflict? A private method in an homonym class.
names::n2$P$p MMethodDef names/n2.nit:31,2--32,13 Name conflict? A private method in an homonym class.
names1 MPackage names1.nit An alternative second module in a distinct package
names1> MGroup names1.nit An alternative second module in a distinct package
names1::names1$names::A MClassDef names1.nit:20,1--30,3 A refinement of a class
names1::names1$names::A$a MMethodDef names1.nit:22,2--23,19 A refinement in the same class
names1::names1$names::A$z MMethodDef names1.nit:25,2--26,19 A refinement in the same class
-names1::names1::A::b MMethod names1.nit:28,2--29,13
+names1::names1::A::b MMethod names1.nit:28,2--29,13 A public method introduced in a refinement
names1::names1$names::A$b MMethodDef names1.nit:28,2--29,13 A public method introduced in a refinement
names1::names1$names::A0 MClassDef names1.nit:32,1--42,3 A refinement of a subclass
names1::names1$names::A0$names::A::a MMethodDef names1.nit:34,2--35,19 A refinement+redefinition
names1::names1$names::A0$names::n0::A::z MMethodDef names1.nit:37,2--38,19 A refinement+redefinition
names1::names1$names::A0$names::n0::P::p MMethodDef names1.nit:40,2--41,19 A refinement+redefinition
-names1::A1 MClass names1.nit:44,1--57,3
+names1::A1 MClass names1.nit:44,1--57,3 A subclass introduced in a submodule
names1$A1 MClassDef names1.nit:44,1--57,3 A subclass introduced in a submodule
names1$A1$names::A::a MMethodDef names1.nit:49,2--50,19 A redefinition in a subclass from a different module
names1$A1$names::n0::A::z MMethodDef names1.nit:52,2--53,19 A redefinition in a subclass from a different module
names1::names1$names::n0::P0$names::A::a MMethodDef names1.nit:67,2--68,19 A refinement+redefinition
names1::names1$names::n0::P0$names::n0::A::z MMethodDef names1.nit:70,2--71,19 A refinement+redefinition
names1::names1$names::n0::P0$names::n0::P::p MMethodDef names1.nit:73,2--74,19 A refinement+redefinition
-names1::names1::P1 MClass names1.nit:77,1--90,3
+names1::names1::P1 MClass names1.nit:77,1--90,3 A private subclass introduced in a different module
names1::names1$P1 MClassDef names1.nit:77,1--90,3 A private subclass introduced in a different module
names1::names1$P1$names::A::a MMethodDef names1.nit:82,2--83,19 A redefinition in a subclass from a different module
names1::names1$P1$names::n0::A::z MMethodDef names1.nit:85,2--86,19 A redefinition in a subclass from a different module
--- /dev/null
+S&éstrS&éstr
-Runtime error: Cast failed. Expected `E`, got `Bool` (../lib/core/collection/array.nit:989)
+Runtime error: Cast failed. Expected `E`, got `Bool` (../lib/core/collection/array.nit:991)
NativeString
0x4e
Nit
--- /dev/null
+prompt>line 1
+line 1
+prompt>line 2
+line 2
+prompt>line 2bis
+line 2bis
+prompt>line 3 \b \bine\b \b\b \b\b \b3\b \b
+line 3
+prompt>
\ No newline at end of file
+++ /dev/null
-sleeping 1s
-true
-true
-sleeping 5000ns
-true
-true
-true
--- /dev/null
+# This file is part of NIT ( http://www.nitlanguage.org ).
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+
+import core
+#alt1 intrude import core::text::ropes
+#alt2 intrude import core::text::ropes
+
+var ons = new NativeString(9)
+var base_str = "%Dégâštr"
+
+var str: String = base_str
+#alt1 str = new Concat(base_str, base_str)
+#alt2 str = new Concat(base_str, base_str.substring_from(2))
+
+var copy_len = (str.bytelen - 4).min(9)
+str.copy_to_native(ons, copy_len, 4, 0)
+print ons.to_s_with_length(copy_len)
var p = new Process("sleep", "10")
# Send some signals
-p.signal(sigalarm)
+p.signal sigalarm
p.kill
# Wait for it to die
p.wait
-var lapse = clock.lapse
# Let's be generous here, as long as it does not take 5 secs out of 10 it's OK
-print lapse.sec < 5
+print clock.lapse < 5.0
--- /dev/null
+# This file is part of NIT ( http://www.nitlanguage.org ).
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+
+#alt1 intrude import core::text::ropes
+import core
+
+var src_s = "S&éstr"
+var cpstr: Text = src_s
+#alt1 cpstr = new Concat(src_s, src_s)
+#alt2 cpstr = new FlatBuffer.from(src_s)
+#alt3 cpstr = cpstr.substring(1, 5)
+
+var ns = new NativeString(cpstr.bytelen)
+ns.fill_from(cpstr)
+
+print ns.to_s_with_length(cpstr.bytelen)
redef class Sys
var iface: String is lazy do
- srand
- return "localhost:{10000+20000.rand}"
+ var testid = "NIT_TESTING_ID".environ.to_i
+ return "localhost:{10000+testid}"
end
var fs_path: String = getcwd / "../lib/nitcorn/examples/www/hello_world/dir" is lazy
# assert undefined_identifier
fun foo do end
+ # a 'failure' unit test (does not parse)
+ # assert !@#$%^&*()
fun foo1(a, b: Int) do end
private fun foo2: Bool do return true
--- /dev/null
+# This file is part of NIT ( http://www.nitlanguage.org ).
+#
+# Copyright 2016 Guilherme Mansur <guilhermerpmansur@gmail.com>
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+
+module test_postgres_nity
+
+import postgresql::postgres
+
+var db = new Postgres.open("dbname=postgres")
+assert open_db: not db.is_closed else print db.error
+
+assert create_table: db.create_table("IF NOT EXISTS users (uname TEXT PRIMARY KEY, pass TEXT NOT NULL, activated INTEGER, perc FLOAT)") else
+ print db.error
+end
+
+assert insert1: db.insert("INTO users VALUES('Bob', 'zzz', 1, 77.7)") else
+ print db.error
+end
+
+assert insert2: db.insert("INTO users VALUES('Guilherme', 'xxx', 1, 88)") else
+ print db.error
+end
+
+var result = db.raw_execute("SELECT * FROM users")
+
+assert raw_exec: result.is_ok else print db.error
+
+assert postgres_nfields: result.nfields == 4 else print_error db.error
+assert postgres_fname: result.fname(0) == "uname" else print_error db.error
+assert postgres_isnull: result.is_null(0,0) == false else print_error db.error
+assert postgres_value: result.value(0,0) == "Bob" else print_error db.error
+
+assert drop_table: db.execute("DROP TABLE users") else print db.error
+
+db.finish
+
+assert db.is_closed else print db.error
--- /dev/null
+line 1
+line 2
+line 2bis
+line 3 \bine\b\b\b3\b
--- /dev/null
+# This file is part of NIT ( http://www.nitlanguage.org ).
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+
+import readline
+
+loop
+ var line = readline("prompt>", true)
+ if line == null then break
+ print line
+end
export LANG=C
export LC_ALL=C
export NIT_TESTING=true
+# Use the pid as a collision prevention
+export NIT_TESTING_ID=$$
export NIT_SRAND=0
unset NIT_DIR