diff --git a/core/doctype/documentation_tool/__init__.py b/core/doctype/documentation_tool/__init__.py
deleted file mode 100644
index cebc5adf82..0000000000
--- a/core/doctype/documentation_tool/__init__.py
+++ /dev/null
@@ -1,3 +0,0 @@
-# Copyright (c) 2013, Web Notes Technologies Pvt. Ltd. and Contributors
-# MIT License. See license.txt
-
diff --git a/core/doctype/documentation_tool/docs.css b/core/doctype/documentation_tool/docs.css
deleted file mode 100644
index add040b063..0000000000
--- a/core/doctype/documentation_tool/docs.css
+++ /dev/null
@@ -1,77 +0,0 @@
-@import url(http://fonts.googleapis.com/css?family=Noticia+Text);
-@import url(http://fonts.googleapis.com/css?family=Open+Sans);
-
-body {
- font-family: "Noticia Text", Serif;
- font-size: 16px;
- text-rendering: optimizeLegibility;
- color: #222;
- line-height: 1.8;
-}
-
-h1, h2, h3, h4, .navbar {
- font-family: "Open Sans", Sans-Serif;
-}
-
-h1, h2, h3, h4, h5 {
- font-weight: bold;
-}
-
-img {
- max-width: 100%;
-}
-
-.container {
- max-width: 767px;
-}
-
-.navbar {
- background-color: #ffffff;
- border-bottom: 5px solid #c0392b;
- border-radius: 0px;
-}
-
-.navbar .navbar-nav > li > a:hover
-{
- color: #444444;
-}
-
-h1, h2, h3 {
- font-weight: bold;
-}
-
- .logo {
- font-weight: bold;
-}
-
-li {
- line-height: inherit;
-}
-
-.content img {
- border-radius: 5px;
-}
-
-blockquote {
- padding: 10px 0 10px 15px;
- margin: 0 0 20px;
- background-color: #FFFCED;
- border-left: 5px solid #fbeed5;
-}
-
-blockquote p {
- margin-bottom: 0;
- font-size: 16px;
- font-weight: normal;
- line-height: 25px;
-}
-
-.erpnext-logo {
- width: 32px;
- height: 32px;
- margin: -11px 0px;
-}
-
-.erpnext-logo rect {
- fill: #ffffff !important;
-}
\ No newline at end of file
diff --git a/core/doctype/documentation_tool/docs.html b/core/doctype/documentation_tool/docs.html
deleted file mode 100644
index 22d91e9137..0000000000
--- a/core/doctype/documentation_tool/docs.html
+++ /dev/null
@@ -1,101 +0,0 @@
-
-
-
- "),
- original_cur_frm = cur_frm;
- doc = cur_frm.doc;
- make_page = function(name, links) {
- body.empty();
- var page = new wn.docs.DocsPage({
- namespace: name,
- parent: body,
- links: links
- });
-
- var for_namespace = (
- doc.build_pages ? doc.page_name :
- (doc.build_modules ? null : (
- doc.build_server_api ? doc.python_module_name : null)));
-
- page.write(for_namespace);
-
- // make_page for _toc items
- var pages = (page.obj._toc || []).concat(page.obj._links || []);
- if(pages && pages.length) {
- $.each(pages, function(i, child_name) {
- var parent_name = child_name.split(".").slice(0,-1).join("."),
- child_links = {
- parent: parent_name
- }
- parentobj = wn.provide(parent_name);
-
- if(parentobj._toc) {
- $.each(parentobj._toc, function(j, sibling) {
- if(sibling===child_name && j!==parentobj._toc.length-1)
- child_links.next_sibling = parentobj._toc[i+1];
- })
- }
- var docs_full_name = wn.docs.get_full_name(child_name);
- if(!wn.docs.to_write[docs_full_name]) {
- make_page(docs_full_name, child_links);
- }
- });
- }
- }
-
- logarea.empty().append("Downloading server docs...
");
-
- return wn.call({
- "method": "core.doctype.documentation_tool.documentation_tool.get_docs",
- args: {options: cur_frm.doc},
- callback: function(r) {
-
- // append
- wn.provide("docs.dev").modules = r.message.modules;
- wn.provide("docs.dev.framework.server").webnotes = r.message.webnotes;
- wn.provide("docs.dev.framework.client").wn = wn;
-
- if(!docs._links) docs._links = [];
-
- // append static pages to the "docs" object
- $.each(r.message.pages || [], function(n, obj) {
- $.extend(wn.provide(n), obj);
- });
-
- logarea.append("Preparing html...
");
-
- make_page("docs");
-
- logarea.append("Writing...
");
- return wn.call({
- method: "core.doctype.documentation_tool.documentation_tool.write_docs",
- args: {
- data: JSON.stringify(wn.docs.to_write),
- build_sitemap: doc.build_sitemap,
- domain: doc.sitemap_domain
- },
- callback: function(r) {
- logarea.append("Wrote " + keys(wn.docs.to_write).length + " pages.");
- cur_frm = original_cur_frm;
- }
- });
- }
- });
-}
-
-wn.docs.build_client_app_toc = function(obj, obj_name) {
- var is_module = function(value) {
- return value
- && $.isPlainObject(value)
- && value._type !== "instance"
- && has_function_or_class(value)
- }
- var has_function_or_class = function(value) {
- var ret = false;
- $.each(value, function(name, prop) {
- if(prop &&
- (typeof prop === "function"
- || prop._type === "class")
- && prop._type !== "instance") {
- ret = true;
- return false;
- }
- })
- return ret
- }
- if($.isPlainObject(obj)) {
- var toc = [];
- $.each(obj, function(name, value) {
- if(value) {
- if(is_module(value) || value._type==="class")
- toc.push(obj_name + "." + name);
- }
- });
- if(toc.length) {
- obj._toc = toc;
- $.each(toc, function(i, full_name) {
- var name = full_name.split(".").slice(-1)[0];
- wn.docs.build_client_app_toc(obj[name], full_name);
- })
- }
- }
-}
-
-wn.docs.get_full_name = function(name) {
- /* docs:
- Get full name with docs namespace
- */
- var link_name = name;
- if(name.substr(0,2)==="wn") {
- link_name = "docs.dev.framework.client." + name;
- }
- if(name.substr(0,8)==="webnotes") {
- link_name = "docs.dev.framework.server." + name;
- }
- return link_name;
-}
-
-wn.docs.get_short_name = function(namespace) {
- namespace = namespace.replace("docs.dev.framework.server.", "")
- namespace = namespace.replace("docs.dev.framework.client.", "")
- return namespace;
-}
-
-wn.docs.get_title = function(namespace) {
- var obj = wn.provide(namespace);
- return obj._label || wn.docs.get_short_name(namespace)
-}
-
-wn.docs.DocsPage = Class.extend({
- init: function(opts) {
- /* docs: create js documentation */
- $.extend(this, opts);
-
- var obj = wn.provide(this.namespace),
- me = this;
-
- obj = (obj._type == "class" && obj.prototype) ? obj.prototype : obj;
- if(obj._toc && this.links)
- this.links.first_child = obj._toc[0];
-
- this.obj = obj;
- this.make(obj);
- },
- make: function(obj) {
- var has_docs = false;
- this.make_title(obj);
- this.make_breadcrumbs(obj);
- has_docs = this.make_intro(obj);
- has_docs = this.make_toc(obj) || has_docs;
- if(obj._type==="model") {
- this.make_docproperties(obj);
- this.make_docfields(obj);
- has_docs = true;
- }
- if(obj._type=="permissions") {
- this.make_docperms(obj);
- has_docs = true;
- }
- if(obj._type==="controller_client") {
- try {
- this.make_obj_from_cur_frm(obj);
- } catch(e) {
- console.log("Failed: " + obj._label);
- console.log(e);
- }
- }
-
- has_docs = this.make_functions(obj) || has_docs;
-
- if(!has_docs) {
- $('
No docs
').appendTo(this.parent);
- }
-
- if(this.links) {
- this.make_links();
- }
- },
- make_links: function() {
- if(this.links.parent) {
- this.obj._parent_title = wn.docs.get_title(this.links.parent);
- this.obj._parent_page = wn.docs.get_full_name(this.links.parent) + ".html";
-
-
- if(this.links.next_sibling) {
- this.obj._next_title = wn.docs.get_title(this.links.next_sibling);
- this.obj._next_page = wn.docs.get_full_name(this.links.next_sibling) + ".html";
- }
-
- if (this.links.first_child) {
- this.obj._child_title = wn.docs.get_title(this.links.first_child);
- this.obj._child_page = wn.docs.get_full_name(this.links.first_child) + ".html";
- }
- }
- },
- make_title: function(obj) {
- if(!obj._no_title) {
- var page_icon = obj._icon;
- if(!obj._icon) {
- if(this.namespace.indexOf(".wn.")!==-1)
- obj._icon = "code";
- else
- obj._icon = "file-text-alt";
- }
-
- if(!obj._label) obj._label = wn.docs.get_short_name(this.namespace)
- }
- },
- make_breadcrumbs: function(obj) {
- var me = this,
- name = this.namespace
-
- if(name==="docs") return;
-
- obj._breadcrumbs = [];
-
- var parts = name.split("."),
- fullname = "";
-
- $.each(parts, function(i, p) {
- if(i!=parts.length-1) {
- fullname = fullname + (fullname ? "." : "") + p;
-
- obj._breadcrumbs.push({
- link: (fullname==="docs" ? "index" : fullname) + ".html",
- label: wn.provide(fullname)._label || p
- })
- }
- });
- },
- make_intro: function(obj) {
- if(obj._intro) {
- $("
").html(wn.markdown(obj._intro)).appendTo(this.parent);
- return true;
- }
- },
- make_toc: function(obj) {
- if(obj._toc && !obj._no_toc) {
- obj._toc_links = [];
- $.each(obj._toc, function(i, name) {
- var link_name = wn.docs.get_full_name(name);
- obj._toc_links.push({
- link: link_name + ".html",
- label: wn.provide(link_name)._label || name
- });
- });
- return true;
- }
- },
-
- make_docproperties: function(obj) {
- var me = this;
-
- this.h3("Properties");
- var tbody = this.get_tbody([
- {label:"Property", width: "25%"},
- {label:"Value", width: "25%"},
- {label:"Description", width: "50%"},
- ]);
-
- $.each(wn.model.get("DocField", {parent:"DocType"}), function(i, df) {
- if(wn.model.no_value_type.indexOf(df.fieldtype)===-1) {
- if(!df.description)
- df.description = "";
- df.value = obj._properties[df.fieldname]==null || "";
- if(df.value!=="") {
- $(repl('
\
- | %(label)s | \
- %(value)s | \
- %(description)s | \
-
', df)).appendTo(tbody);
- }
- }
- });
- },
-
- make_docfields: function(obj) {
- var me = this,
- docfields = obj._fields;
-
- if(docfields.length) {
- this.h3("DocFields");
- var tbody = this.get_tbody([
- {label:"Sr", width: "10%"},
- {label:"Fieldname", width: "25%"},
- {label:"Label", width: "20%"},
- {label:"Field Type", width: "25%"},
- {label:"Options", width: "20%"},
- ]);
- docfields = docfields.sort(function(a, b) { return a.idx > b.idx ? 1 : -1 })
- $.each(docfields, function(i, df) {
- $(repl('
\
- | %(idx)s | \
- %(fieldname)s | \
- %(label)s | \
- %(fieldtype)s | \
- %(options)s | \
-
', df)).appendTo(tbody);
- });
- };
- },
- make_docperms: function(obj) {
- var me = this;
- if(obj._permissions.length) {
- this.h3("Permissions");
- var tbody = this.get_tbody([
- {label:"Sr", width: "8%"},
- {label:"Role", width: "20%"},
- {label:"Level", width: "7%"},
- {label:"Read", width: "7%"},
- {label:"Write", width: "8%"},
- {label:"Create", width: "8%"},
- {label:"Submit", width: "8%"},
- {label:"Cancel", width: "8%"},
- {label:"Amend", width: "8%"},
- {label:"Report", width: "8%"},
- {label:"Match", width: "10%"},
- ]);
- obj._permissions = obj._permissions.sort(function(a, b) {
- return a.idx > b.idx ? 1 : -1
- })
- $.each(obj._permissions, function(i, perm) {
- if(!perm.match) perm.match = "";
- $.each(["permlevel", "read", "write", "cancel", "create", "submit",
- "amend", "report", "match"], function(i, key) {
- if(perm[key]==null) perm[key] = "";
- });
- $(repl('
\
- | %(idx)s | \
- %(role)s | \
- %(permlevel)s | \
- %(read)s | \
- %(write)s | \
- %(create)s | \
- %(submit)s | \
- %(cancel)s | \
- %(amend)s | \
- %(report)s | \
- %(match)s | \
-
', perm)).appendTo(tbody);
- });
- };
- },
- make_obj_from_cur_frm: function(obj) {
- var me = this;
- obj._fetches = [];
- cur_frm = {
- set_query: function() {
-
- },
- cscript: {},
- pformat: {},
- add_fetch: function() {
- obj._fetches.push(arguments)
- },
- fields_dict: {},
- call: function() {
-
- }
- };
- $.each(obj._fields, function(i, f) {
- cur_frm.fields_dict[f] = {
- grid: {
- get_field: function(fieldname) {
- return {}
- }
- }
- }}
- );
- var tmp = eval(obj._code);
- $.extend(obj, cur_frm.cscript);
- },
- make_functions: function(obj) {
- var functions = this.get_functions(obj);
- if(!$.isEmptyObject(functions)) {
- this.h3(obj._type === "class" ? "Methods" : "Functions");
- this.make_function_table(functions);
- return true;
- }
- },
- get_functions: function(obj) {
- var functions = {};
-
- $.each(obj || {}, function(name, value) {
- if(value && ((typeof value==="function" && typeof value.init !== "function")
- || value._type === "function"))
- functions[name] = value;
- });
- return functions;
- },
- make_function_table: function(functions, namespace) {
- var me = this,
- tbody = this.get_tbody();
-
- $.each(functions || {}, function(name, value) {
- me.render_function(name, value, tbody, namespace)
- });
- },
- get_tbody: function(columns) {
- table = $("
").appendTo(this.parent);
- if(columns) {
- $.each(columns || [], function(i, c) {
- $("
")
- .css({"width": c.width})
- .html(c.label)
- .appendTo(table.find("thead"))
- });
- }
- return table.find("tbody");
- },
- h3: function(txt) {
- $("").html(txt).appendTo(this.parent);
- },
- render_function: function(name, value, parent, namespace) {
- var me = this,
- code = value.toString();
-
- namespace = namespace===undefined ?
- ((this.obj._type==="class" || this.obj._type==="controller_client") ?
- "" : this.namespace)
- : "";
-
- if(this.obj._function_namespace)
- namespace = this.obj._function_namespace;
-
- if(namespace!=="") {
- namespace = wn.docs.get_short_name(namespace);
- }
-
- if(namespace!=="" && namespace[namespace.length-1]!==".")
- namespace = namespace + ".";
-
- var args = this.get_args(value);
-
- var help = value._help || code.split("/* docs:")[1];
- if(help && help.indexOf("*/")!==-1) help = help.split("*/")[0];
-
- var source = "";
- if(code.substr(0, 8)==="function" || value._source) {
- source = repl('\
- View Source \
- \
-%(code)s ', {
- name: name,
- code: value._source || code,
- lang: (value._source ? "python" : "javascript")
- });
- }
-
- try {
- $(repl(' | \
- | %(name)s | \
- \
- Usage:\
- %(namespace)s%(name)s(%(args)s) \
- %(help)s\
- %(source)s\
- | \
-
', {
- name: name,
- namespace: namespace,
- args: args,
- help: help ? wn.markdown(help) : "",
- source: source
- })).appendTo(parent)
- } catch(e) {
- console.log("Possible html embedded in: " + name)
- console.log(e);
- }
- },
- get_args: function(obj) {
- if(obj._args)
- return obj._args.join(", ");
- else
- return obj.toString().split("function")[1].split("(")[1].split(")")[0];
- },
- write: function(callback, for_namespace) {
- var me = this;
- if(for_namespace && for_namespace!==this.namespace) {
- callback();
- return;
- }
-
- var args = {};
- $.each(["_label", "_gh_source", "_modified", "_parent_title", "_parent_page",
- "_next_title", "_next_page", "_child_title", "_child_page", "_no_title",
- "_breadcrumbs", "_toc_links"], function(i, key) {
- if(me.obj[key])
- args[key] = me.obj[key]
- })
-
- args.content = html_beautify(this.parent.html())
-
- wn.docs.to_write[this.namespace] = args;
- }
-})
\ No newline at end of file
diff --git a/core/doctype/documentation_tool/documentation_tool.py b/core/doctype/documentation_tool/documentation_tool.py
deleted file mode 100644
index cc2db032e7..0000000000
--- a/core/doctype/documentation_tool/documentation_tool.py
+++ /dev/null
@@ -1,520 +0,0 @@
-# Copyright (c) 2013, Web Notes Technologies Pvt. Ltd. and Contributors
-# MIT License. See license.txt
-
-# For license information, please see license.txt
-
-from __future__ import unicode_literals
-
-import webnotes
-import inspect, os, json, datetime, shutil
-from webnotes.modules import get_doc_path, get_module_path, scrub
-from webnotes.utils import get_path, get_base_path, cstr
-
-class DocType:
- def __init__(self, d, dl):
- self.doc, self.doclist = d, dl
-
- def onload(self):
- prepare_docs()
-
-gh_prefix = "https://github.com/webnotes/"
-
-@webnotes.whitelist()
-def get_docs(options):
- docs = {}
- options = webnotes._dict(json.loads(options))
- if options.build_server_api:
- get_docs_for(docs, "webnotes")
- if options.build_modules:
- docs["modules"] = get_modules(options.module_name)
- if options.build_pages:
- docs["pages"] = get_static_pages()
- return docs
-
-def get_static_pages():
- mydocs = {}
- for repo in ("lib", "app"):
- for basepath, folders, files in os.walk(get_path(repo, "docs")):
- for fname in files:
- fname = cstr(fname)
- if fname.endswith(".md"):
- fpath = get_path(basepath, fname)
- with open(fpath, "r") as docfile:
- src = unicode(docfile.read(), "utf-8")
- try:
- temp, headers, body = src.split("---", 2)
- d = json.loads(headers)
- except Exception, e:
- webnotes.msgprint("Bad Headers in: " + fname)
- continue
- d["_intro"] = body
- d["_gh_source"] = get_gh_url(fpath)
- d["_modified"] = get_timestamp(fpath)
- mydocs[fname[:-3]] = d
-
- return mydocs
-
-def get_docs_for(docs, name):
- """build docs for python module"""
- import importlib
- classname = ""
- parts = name.split(".")
-
- if not parts[-1] in docs:
- docs[parts[-1]] = {}
-
- mydocs = docs[parts[-1]]
- try:
- obj = importlib.import_module(name)
- except ImportError:
- # class
- name, classname = ".".join(parts[:-1]), parts[-1]
- module = importlib.import_module(name)
- obj = getattr(module, classname)
-
- inspect_object_and_update_docs(mydocs, obj)
-
- # if filename is __init__, list python files and folders with init in folder as _toc
- if hasattr(obj, "__file__") and os.path.basename(obj.__file__).split(".")[0]=="__init__":
- mydocs["_toc"] = []
- dirname = os.path.dirname(obj.__file__)
- for fname in os.listdir(dirname):
- fname = cstr(fname)
- fpath = os.path.join(dirname, fname)
- if os.path.isdir(fpath):
- # append if package
- if "__init__.py" in os.listdir(fpath):
- mydocs["_toc"].append(name + "." + fname)
- elif fname.endswith(".py") and not fname.startswith("__init__") and \
- not fname.startswith("test_"):
- # append if module
- mydocs["_toc"].append(name + "." + fname.split(".")[0])
-
- if mydocs.get("_toc"):
- for name in mydocs["_toc"]:
- get_docs_for(mydocs, name)
-
- return mydocs
-
-def inspect_object_and_update_docs(mydocs, obj):
- mydocs["_toc"] = getattr(obj, "_toc", "")
- if inspect.ismodule(obj):
- obj_module = obj
- mydocs["_type"] = "module"
- else:
- obj_module = inspect.getmodule(obj)
- mydocs["_type"] = "class"
-
- mydocs["_icon"] = "code"
- mydocs["_gh_source"] = get_gh_url(obj_module.__file__)
- mydocs["_modified"] = get_timestamp(obj_module.__file__)
-
- if not mydocs.get("_intro"):
- mydocs["_intro"] = getattr(obj, "__doc__", "")
-
- for name in dir(obj):
- try:
- value = getattr(obj, name)
- except AttributeError, e:
- value = None
-
- if value:
- if (mydocs["_type"]=="module" and inspect.getmodule(value)==obj)\
- or (mydocs["_type"]=="class" and getattr(value, "im_class", None)==obj):
- if inspect.ismethod(value) or inspect.isfunction(value):
- mydocs[name] = {
- "_type": "function",
- "_args": inspect.getargspec(value)[0],
- "_help": getattr(value, "__doc__", ""),
- "_source": inspect.getsource(value)
- }
- elif inspect.isclass(value):
- if not mydocs.get("_toc"):
- mydocs["_toc"] = []
- mydocs["_toc"].append(obj.__name__ + "." + value.__name__)
-
-def get_gh_url(path):
- sep = "/lib/" if "/lib/" in path else "/app/"
- url = gh_prefix \
- + ("wnframework" if sep=="/lib/" else "erpnext") \
- + ("/blob" if ("." in path) else "/tree") \
- +"/master/" + path.split(sep)[1]
- if url.endswith(".pyc"):
- url = url[:-1]
- return url
-
-def get_modules(for_module=None):
- import importlib
- docs = {
- "_label": "Modules"
- }
- if for_module:
- modules = [for_module]
- else:
- modules = webnotes.conn.sql_list("select name from `tabModule Def` order by name")
-
- docs["_toc"] = ["docs.dev.modules." + d for d in modules]
- for m in modules:
- prefix = "docs.dev.modules." + m
- mydocs = docs[m] = {
- "_icon": "th",
- "_label": m,
- "_toc": [
- prefix + ".doctype",
- prefix + ".page",
- prefix + ".py_modules"
- ],
- "doctype": get_doctypes(m),
- "page": get_pages(m),
- #"report": {},
- "py_modules": {
- "_label": "Independent Python Modules for " + m,
- "_toc": []
- }
- }
-
- # add stand alone modules
- module_path = get_module_path(m)
- prefix = prefix + ".py_modules."
- for basepath, folders, files in os.walk(module_path):
- for f in files:
- f = cstr(f)
- if f.endswith(".py") and \
- (not f.split(".")[0] in os.path.split(basepath)) and \
- (not f.startswith("__")):
-
- module_name = ".".join(os.path.relpath(os.path.join(basepath, f),
- "../app").split(os.path.sep))[:-3]
-
- # import module
- try:
- module = importlib.import_module(module_name)
- # create a new namespace for the module
- module_docs = mydocs["py_modules"][f.split(".")[0]] = {}
-
- # add to toc
- mydocs["py_modules"]["_toc"].append(prefix + f.split(".")[0])
-
- inspect_object_and_update_docs(module_docs, module)
- except TypeError, e:
- webnotes.errprint("TypeError in importing " + module_name)
- except IndentationError, e:
- continue
-
- module_docs["_label"] = module_name
- module_docs["_function_namespace"] = module_name
-
- update_readme(docs[m], m)
- docs[m]["_gh_source"] = get_gh_url(module_path)
-
- return docs
-
-def get_pages(m):
- import importlib
- pages = webnotes.conn.sql_list("""select name from tabPage where module=%s""", m)
- prefix = "docs.dev.modules." + m + ".page."
- docs = {
- "_icon": "file-alt",
- "_label": "Pages",
- "_toc": [prefix + d for d in pages]
- }
- for p in pages:
- page = webnotes.doc("Page", p)
- mydocs = docs[p] = {
- "_label": page.title or p,
- "_type": "page",
- }
- update_readme(mydocs, m, "page", p)
- mydocs["_modified"] = page.modified
-
- # controller
- page_name = scrub(p)
- try:
- page_controller = importlib.import_module(scrub(m) + ".page." + page_name + "." + page_name)
- inspect_object_and_update_docs(mydocs, page_controller)
- except ImportError, e:
- pass
-
- return docs
-
-def get_doctypes(m):
- doctypes = webnotes.conn.sql_list("""select name from
- tabDocType where module=%s order by name""", m)
- prefix = "docs.dev.modules." + m + ".doctype."
- docs = {
- "_icon": "th",
- "_label": "DocTypes",
- "_toc": [prefix + d for d in doctypes]
- }
-
- for d in doctypes:
- meta = webnotes.get_doctype(d)
- meta_p = webnotes.get_doctype(d, True)
- doc_path = get_doc_path(m, "DocType", d)
-
- mydocs = docs[d] = {
- "_label": d,
- "_icon": meta[0].icon,
- "_type": "doctype",
- "_gh_source": get_gh_url(doc_path),
- "_toc": [
- prefix + d + ".model",
- prefix + d + ".permissions",
- prefix + d + ".controller_server"
- ],
- }
-
- update_readme(mydocs, m, "DocType", d)
-
- # parents and links
- links, parents = [], []
- for df in webnotes.conn.sql("""select * from tabDocField where options=%s""",
- d, as_dict=True):
- if df.parent:
- if df.fieldtype=="Table":
- parents.append(df.parent)
- if df.fieldtype=="Link":
- links.append(df.parent)
-
- if parents:
- mydocs["_intro"] += "\n\n#### Child Table Of:\n\n- " + "\n- ".join(list(set(parents))) + "\n\n"
-
- if links:
- mydocs["_intro"] += "\n\n#### Linked In:\n\n- " + "\n- ".join(list(set(links))) + "\n\n"
-
- if meta[0].issingle:
- mydocs["_intro"] += "\n\n#### Single DocType\n\nThere is no table for this DocType and the values of the Single instance are stored in `tabSingles`"
-
- # model
- modeldocs = mydocs["model"] = {
- "_label": d + " Model",
- "_icon": meta[0].icon,
- "_type": "model",
- "_intro": "Properties and fields for " + d,
- "_gh_source": get_gh_url(os.path.join(doc_path, scrub(d) + ".txt")),
- "_fields": [df.fields for df in meta.get({"doctype": "DocField"})],
- "_properties": meta[0].fields,
- "_modified": meta[0].modified
- }
-
- # permissions
- from webnotes.modules.utils import peval_doclist
- with open(os.path.join(doc_path,
- scrub(d) + ".txt"), "r") as txtfile:
- doclist = peval_doclist(txtfile.read())
-
- permission_docs = mydocs["permissions"] = {
- "_label": d + " Permissions",
- "_type": "permissions",
- "_icon": meta[0].icon,
- "_gh_source": get_gh_url(os.path.join(doc_path, scrub(d) + ".txt")),
- "_intro": "Standard Permissions for " + d + ". These can be changed by the user.",
- "_permissions": [p for p in doclist if p.doctype=="DocPerm"],
- "_modified": doclist[0]["modified"]
- }
-
- # server controller
- server_controller_path = os.path.join(doc_path, scrub(d) + ".py")
- controller_docs = mydocs["controller_server"] = {
- "_label": d + " Server Controller",
- "_type": "_class",
- "_gh_source": get_gh_url(server_controller_path)
- }
-
- b = webnotes.bean([{"doctype": d}])
- b.make_controller()
- if not getattr(b.controller, "__doc__"):
- b.controller.__doc__ = "Controller Class for handling server-side events for " + d
- inspect_object_and_update_docs(controller_docs, b.controller)
-
- # client controller
- if meta_p[0].fields.get("__js"):
- client_controller_path = os.path.join(doc_path, scrub(d) + ".js")
- if(os.path.exists(client_controller_path)):
- mydocs["_toc"].append(prefix + d + ".controller_client")
- client_controller = mydocs["controller_client"] = {
- "_label": d + " Client Controller",
- "_icon": meta[0].icon,
- "_type": "controller_client",
- "_gh_source": get_gh_url(client_controller_path),
- "_modified": get_timestamp(client_controller_path),
- "_intro": "Client side triggers and functions for " + d,
- "_code": meta_p[0].fields["__js"],
- "_fields": [d.fieldname for d in meta_p if d.doctype=="DocField"]
- }
-
- return docs
-
-def update_readme(mydocs, module, doctype=None, name=None):
- if doctype:
- readme_path = os.path.join(get_doc_path(module, doctype, name), "README.md")
- else:
- readme_path = os.path.join(get_module_path(module), "README.md")
-
- mydocs["_intro"] = ""
-
- if os.path.exists(readme_path):
- with open(readme_path, "r") as readmefile:
- mydocs["_intro"] = readmefile.read()
- mydocs["_modified"] = get_timestamp(readme_path)
-
-def prepare_docs(force=False):
- os.chdir(get_path("public"))
- if not os.path.exists("docs"):
- os.mkdir("docs")
-
- if force:
- shutil.rmtree("docs/css")
-
- if not os.path.exists("docs/css"):
- os.mkdir("docs/css")
- os.mkdir("docs/css/font")
- os.system("cp ../lib/public/css/bootstrap.css docs/css")
- os.system("cp ../lib/public/css/font-awesome.css docs/css")
- os.system("cp ../lib/public/css/font/* docs/css/font")
- os.system("cp ../lib/public/css/prism.css docs/css")
-
- # clean links in font-awesome
- with open("docs/css/font-awesome.css", "r") as fontawesome:
- t = fontawesome.read()
- t = t.replace("../lib/css/", "")
- with open("docs/css/font-awesome.css", "w") as fontawesome:
- fontawesome.write(t)
-
- # copy latest docs.css
- os.system("cp ../lib/core/doctype/documentation_tool/docs.css docs/css")
-
-
- if force:
- shutil.rmtree("docs/js")
-
- if not os.path.exists("docs/js"):
- os.mkdir("docs/js")
- os.system("cp ../lib/public/js/lib/bootstrap.min.js docs/js")
- os.system("cp ../lib/public/js/lib/jquery/jquery.min.js docs/js")
- os.system("cp ../lib/public/js/lib/prism.js docs/js")
-
- if force:
- os.remove("docs/img/splash.svg")
-
- if not os.path.exists("docs/img/splash.svg"):
- if not os.path.exists("docs/img"):
- os.mkdir("docs/img")
- os.system("cp ../app/public/images/splash.svg docs/img")
-
-@webnotes.whitelist()
-def write_docs(data, build_sitemap=None, domain=None):
- from webnotes.utils import global_date_format
- if webnotes.session.user != "Administrator":
- raise webnotes.PermissionError
-
- if isinstance(data, basestring):
- data = json.loads(data)
-
- template = webnotes.get_template("app/docs/templates/docs.html")
-
- data["index"] = data["docs"]
- data["docs"] = None
- for name, d in data.items():
- if d:
- if not d.get("title"):
- d["title"] = d["_label"]
- if d.get("_parent_page")=="docs.html":
- d["_parent_page"] = "index.html"
- if not d.get("_icon"):
- d["_icon"] = "icon-file-alt"
- if not d["_icon"].startswith("icon-"):
- d["_icon"] = "icon-" + d["_icon"]
- if d.get("_modified"):
- d["_modified"] = global_date_format(d["_modified"])
-
- with open(get_path("public", "docs", name + ".html"), "w") as docfile:
- if not d.get("description"):
- d["description"] = "Help pages for " + d["title"]
- html = template.render(d)
- docfile.write(html.encode("utf-8", errors="ignore"))
-
- if build_sitemap and domain:
- if not domain.endswith("/"):
- domain = domain + "/"
- content = ""
- for fname in os.listdir(get_path("public", "docs")):
- fname = cstr(fname)
- if fname.endswith(".html"):
- content += sitemap_link_xml % (domain + fname,
- get_timestamp(get_path("public", "docs", fname)))
-
- with open(get_path("public", "docs", "sitemap.xml"), "w") as sitemap:
- sitemap.write(sitemap_frame_xml % content)
-
-def write_static():
- webnotes.local.session = webnotes._dict({"user":"Administrator"})
- pages = prepare_static_pages()
- write_docs(pages)
- prepare_docs()
-
-def prepare_static_pages():
- from markdown2 import markdown
-
- pages = get_static_pages()
- autogenerated_roots = ["docs.dev.framework.server", "docs.dev.framework.client",
- "docs.dev.modules"]
-
- # build toc
- for name, page in pages.items():
- if name in autogenerated_roots:
- del pages[name]
- continue
-
- # toc
- if page.get("_toc"):
- prev = None
- page["_toc_links"] = []
- for child in page["_toc"]:
- if child in pages:
- page["_toc_links"].append({
- "link": child + ".html",
- "label": pages[child]["_label"]
- })
-
- if not "_child_title" in page:
- page["_child_title"] = pages[child]["_label"]
- page["_child_page"] = child + ".html"
-
- pages[child]["_parent_title"] = page["_label"]
- pages[child]["_parent_page"] = name + ".html"
-
- if prev:
- prev["_next_title"] = pages[child]["_label"]
- prev["_next_page"] = child + ".html"
-
- prev = pages[child]
-
- # breadcrumbs
- if name!="docs":
- fullname = ""
- page["_breadcrumbs"] = []
- for p in name.split(".")[:-1]:
- fullname = fullname + (fullname and "." or "") + p
- page["_breadcrumbs"].append({
- "link": (fullname=="docs" and "index" or fullname) + ".html",
- "label": pages[fullname]["_label"]
- })
-
- page["content"] = markdown(page["_intro"])
-
- return pages
-
-def get_timestamp(path):
- return datetime.datetime.fromtimestamp(os.path.getmtime(path)).strftime("%Y-%m-%d")
-
-
-sitemap_frame_xml = """
-
%s
-"""
-
-sitemap_link_xml = """\n
%s%s"""
-
-if __name__=="__main__":
- write_static()
-
\ No newline at end of file
diff --git a/core/doctype/documentation_tool/documentation_tool.txt b/core/doctype/documentation_tool/documentation_tool.txt
deleted file mode 100644
index fcbdcab437..0000000000
--- a/core/doctype/documentation_tool/documentation_tool.txt
+++ /dev/null
@@ -1,131 +0,0 @@
-[
- {
- "creation": "2013-06-20 10:40:02",
- "docstatus": 0,
- "modified": "2013-07-05 14:36:00",
- "modified_by": "Administrator",
- "owner": "Administrator"
- },
- {
- "custom": 0,
- "description": "Documentation Generator Console",
- "doctype": "DocType",
- "hide_heading": 0,
- "hide_toolbar": 1,
- "icon": "icon-book",
- "issingle": 1,
- "module": "Core",
- "name": "__common__"
- },
- {
- "doctype": "DocField",
- "name": "__common__",
- "parent": "Documentation Tool",
- "parentfield": "fields",
- "parenttype": "DocType",
- "permlevel": 0
- },
- {
- "create": 1,
- "doctype": "DocPerm",
- "name": "__common__",
- "parent": "Documentation Tool",
- "parentfield": "permissions",
- "parenttype": "DocType",
- "permlevel": 0,
- "read": 1,
- "role": "Administrator",
- "write": 1
- },
- {
- "doctype": "DocType",
- "name": "Documentation Tool"
- },
- {
- "doctype": "DocField",
- "fieldname": "build_pages",
- "fieldtype": "Check",
- "label": "Build Pages"
- },
- {
- "doctype": "DocField",
- "fieldname": "build_modules",
- "fieldtype": "Check",
- "label": "Build Modules"
- },
- {
- "doctype": "DocField",
- "fieldname": "build_server_api",
- "fieldtype": "Check",
- "label": "Build Server API"
- },
- {
- "allow_on_submit": 0,
- "description": "Write sitemap.xml",
- "doctype": "DocField",
- "fieldname": "build_sitemap",
- "fieldtype": "Check",
- "hidden": 0,
- "in_filter": 0,
- "in_list_view": 0,
- "label": "Build Sitemap",
- "no_copy": 0,
- "print_hide": 0,
- "read_only": 0,
- "report_hide": 0,
- "reqd": 0,
- "search_index": 0
- },
- {
- "doctype": "DocField",
- "fieldname": "column_break_4",
- "fieldtype": "Column Break"
- },
- {
- "depends_on": "build_pages",
- "doctype": "DocField",
- "fieldname": "page_name",
- "fieldtype": "Data",
- "label": "Page Name"
- },
- {
- "depends_on": "build_modules",
- "doctype": "DocField",
- "fieldname": "module_name",
- "fieldtype": "Data",
- "hidden": 0,
- "label": "Module Name",
- "read_only": 0,
- "reqd": 0
- },
- {
- "depends_on": "build_server_api",
- "doctype": "DocField",
- "fieldname": "python_module_name",
- "fieldtype": "Data",
- "label": "Python Module Name"
- },
- {
- "depends_on": "build_sitemap",
- "description": "example: http://help.erpnext.com",
- "doctype": "DocField",
- "fieldname": "sitemap_domain",
- "fieldtype": "Data",
- "label": "Sitemap Domain"
- },
- {
- "doctype": "DocField",
- "fieldname": "log",
- "fieldtype": "Section Break",
- "label": "Log"
- },
- {
- "doctype": "DocField",
- "fieldname": "out",
- "fieldtype": "HTML",
- "label": "Out"
- },
- {
- "doctype": "DocPerm"
- }
-]
\ No newline at end of file
diff --git a/docs/docs.attributions.md b/docs/docs.attributions.md
deleted file mode 100644
index b226402608..0000000000
--- a/docs/docs.attributions.md
+++ /dev/null
@@ -1,52 +0,0 @@
----
-{
- "_label": "Attributions"
-}
----
-ERPNext is made using these amazing Open Source Projects.
-
-### System Requirements:
-
-1. [Linux Operating System](http://en.wikipedia.org/wiki/Linux): The operating system that brought a revolution in Open Source software.
-1. [MySQL Database](http://www.mysql.com/): The world's most popular Open Source Database.
-1. [Apache HTTPD web server](http://httpd.apache.org): The Number One HTTP Server On The Internet.
-1. [Memcached](http://memcached.org/): Free & open source, high-performance, distributed memory object caching system.
-
-### Tools and Languages:
-
-1. [Python Programming Language](http://python.org/): The "batteries included" language that lets you write elegant code, quickly. With third-party modules:
- - MySQLdb
- - pytz
- - jinja2
- - markdown2
- - dateutil
- - termcolor
- - python-memcached
- - requests
- - chardet
- - pygeoip
- - dropbox
- - google-api-python-client
-1. [Git - Source Code Management](http://git-scm.com/): Git - Source Code Management
-
-### Libraries and Frameworks
-
-1. [wnframework](https://github.com/webnotes/wnframework): The full stack Python + Javascript web application framework on which ERPNext is built.
-1. [JQuery](http://jquery.com/): The write less, do more Javascript Library.
-1. [JQuery UI](http://jqueryui.com/): A curated set of user interface interactions, effects, widgets, and themes built on top of the jQuery JavaScript Library.
-1. [Bootstrap](http://twitter.github.com/bootstrap/index.html): Sleek, intuitive, and powerful front-end framework for faster and easier web development.
-1. [Font Awesome](http://fortawesome.github.com/Font-Awesome/): The iconic font designed for use with Twitter Bootstrap.
-1. [SlickGrid](https://github.com/mleibman/SlickGrid): A lightning fast JavaScript grid/spreadsheet.
-1. [FullCalendar](http://arshaw.com/fullcalendar/): FullCalendar is a jQuery plugin that provides a full-sized, drag and drop calendar.
-1. [Flot Charting Library](http://www.flotcharts.org/): Attractive JavaScript plotting for jQuery.
-1. [Ace Code Editor](http://ace.ajax.org/): High Performance Code Editor for the web.
-1. [JQuery.Gantt](http://taitems.github.com/jQuery.Gantt/): Draw Gantt charts with the famous jQuery ease of development.
-1. [JQuery Tag-it](http://aehlke.github.io/tag-it/): Simple and configurable tag editing widget with autocomplete support.
-1. [JSColor](http://jscolor.com/): HTML/Javascript Color Picker.
-1. [QUnit](http://qunitjs.com/): A JavaScript Unit Testing framework.
-1. [Downloadify](https://github.com/dcneiner/Downloadify): A tiny javascript + Flash library that enables the creation and download of text files without server interaction.
-1. [GeoLite](http://dev.maxmind.com/geoip/geolite): GeoLite data created by MaxMind, available from
https://www.maxmind.com.
-
----
-
-For more information please write to us at support@erpnext.com
\ No newline at end of file
diff --git a/docs/docs.dev.framework.client.md b/docs/docs.dev.framework.client.md
deleted file mode 100644
index 7f26731cb3..0000000000
--- a/docs/docs.dev.framework.client.md
+++ /dev/null
@@ -1,10 +0,0 @@
----
-{
- "_label": "Client Side - JavaScript",
- "_toc": [
- "wn"
- ]
-}
----
-All `wnframework` methods are linked to the `wn` namespace. Browse through the modules
-to understand the various functions available.
\ No newline at end of file
diff --git a/docs/docs.dev.framework.md b/docs/docs.dev.framework.md
deleted file mode 100644
index b29554cb77..0000000000
--- a/docs/docs.dev.framework.md
+++ /dev/null
@@ -1,23 +0,0 @@
----
-{
- "_label": "Framework",
- "_toc": [
- "docs.dev.framework.server",
- "docs.dev.framework.client"
- ]
-}
----
-wnframework has two major libraries one on the client and other on the server.
-
-### Server
-
-The server-side functions are called by the web server (Apache HTTPD) when a user make a web request. The framework handles user authentication, sessions, permissions, business logic and much more.
-
-Serverside functions are also called when static website pages are generated and via a scheduler for triggering scheduled events.
-
-### Client
-
-Once the user is logged in, a javascript based application is loaded. This application communicates with the server to display data, forms, trigger events, run reports etc.
-
-The application is built on standard 3rd party javascript tools like jQuery, Bootstrap,
-SlickGrid and others.
\ No newline at end of file
diff --git a/docs/docs.dev.framework.server.md b/docs/docs.dev.framework.server.md
deleted file mode 100644
index 625db95ce3..0000000000
--- a/docs/docs.dev.framework.server.md
+++ /dev/null
@@ -1,9 +0,0 @@
----
-{
- "_label": "Server Side - Python",
- "_toc": [
- "webnotes"
- ]
-}
----
-The `webnotes` Python module contains all the functions used to manage the application code.
\ No newline at end of file
diff --git a/docs/docs.dev.quickstart.md b/docs/docs.dev.quickstart.md
deleted file mode 100644
index 12b000edab..0000000000
--- a/docs/docs.dev.quickstart.md
+++ /dev/null
@@ -1,202 +0,0 @@
----
-{
- "_label": "Quickstart"
-}
----
-### Preamble
-
-wnframework is, a Python based, meta-data driven framework. The framework implements
-its own object-relational model (ORM) and provides a rich client interface based on
-Javascript. It is primararily used to develop [ERPNext](https://github.com/webnotes/erpnext)
-
-To develop on wnframework, you must have a basic understanding of how web applications
-and client-server architectures work. On the server-side, requests are handled by Python
-modules via CGI. So each request is a new thread and there is no state preservation on
-the server. Session data is stored in memcached server.
-
-WNFramework also has way you metadata is defined, called a `DocType`. Everything
-object in the system like a Customer or Journal Voucher is a `DocType`.
-
-Overall, be prepared for a slight learning curve. A lot of the inner code / design
-is not very elegant and you might encounter spaghetti at certain places. We are working
-to reduce all of that.
-
----
-
-## Meta data
-
-Base model in wnframework is called a `DocType`. A `DocType` represents a database table,
-a web form and a controller to execute business logic. In classical MVC terms it is all
-three model, view and controller to an extent.
-
-`DocType` objects have `DocField`s that are properties of the model.
-
----
-
-## Client-Server Setup
-
-Let us understand how to setup web folders via ERPNext
-
-An ERPNext setup contains 2 repositories [erpnext](/webnotes/erpnext) and
-[wnframework](/webnotes/wnframework). In the main folder of the erpnext setup there
-are 3 folders:
-
- + lib
- + app
- + public
-
-The **lib** folder represents *wnframework*, the **app** folder represents *erpnext* and
-the **public** folder is served on the web.
-
-To build the public folder for the first time, run this utility from the base folder:
-
-`$ lib/wnf.py -b`
-
-All web pages are served by `public/web.py` and all data requests are served
-by `public/server.py`
-
-The server-side libraries are in `lib/webnotes` and client-side libraries are
-in `lib/public/wn` folders.
-
-### Requests & Routings
-
-There are 2 types of requests, requests for web pages (when the user is not logged in) and
-data requests when the user is logged in. Let us see data requests:
-
-All data requests are made on `public/server.py`. The method and parameters are passed as
-form parameters.
-
-The `cmd` paramter represents the python method to be executed. This is the "routing" used
-in wnframwork. Use the `@webnotes.whitelist()` decorator to whitelist a particular method
-to be accessible by the web.
-
-For example, the request:
-
-`server.py?cmd=accounts.utils.get_account&account_name=Test`
-
-will call the `get_account` method in `app/accounts/utils.py`.
-
-#### Repsonse
-
-The return to that will be sent as a JSON object
-
- {
- "message": "returned by get_account",
- "server_messages":"Any popup messages to be displayed",
- "exc": "Any exceptions encountered"
- }
-
-Once the control is passed on to the method, the response is sent back via JSON.
-
----
-
-## Front End
-
-The front end is a Javascript based client application. You can login by opening the login
-page from your browser. If you have setup your apache routes correctly, just go to
-`localhost/public/login` or equivalent to see the login page. This actually translates
-into `public/web.py?page=login`.
-
-Once you login, you will be redirected to `app.html` that fires up the application front-end.
-
-### URL routing:
-
-Different pages / objects are accessed by url fragments `#`
-
-#### Forms
-
-All objects are accessible via `#Form/[DocType]/[Doument Name]` on the URL.
-
-To open the customer **DocType**, you can go to `#Form/DocType/Customer` or to open
-a Customer, **Customer A**, go to `#Form/Customer/Customer A`
-
-#### Pages
-
-Static pages in the application are accessed by their name. For example, the home
-page called `desktop` can be accessed by `#desktop`
-
-#### Client Application
-
-The client application is bunch of js libraries that help in navigation, rendering
-forms, reports and other components. The application code in `public/js/all-app.js`
-is built by combining files specified in `lib/public/build.json` and `app/public/build.json`.
- To rebuild the client application after making a change, call `lib/wnf.py -b` from the
-command line.
-
----
-
-## Application / Module Development
-
-### Creating / Editing DocTypes
-
-To create or edit the **DocType** "schema" you will have to fire the front-end via a
-web-browser and login as Administrator. To open a **DocType**,
-go to Document > Search > DocType and select the **DocType** to edit.
-
-The **DocType** form should be self explanatory. It has a list of fields that are
-used for both the database table and form. Special fields like `Column Break` and
-`Section Break` are present to make the form layout that is processed sequentially.
-
-DocType is discovered via permissions (`DocPerm`) and by URL routes.
-
-Once you save a **DocType**, the database schema is automatically update, while
-developing, you should fire up a mysql command-line or viewer to see the impact
-of your database changes.
-
-### Adding code to DocTypes
-
-You can add business logic by writing event code on both client and server side.
-The server side events are written in Python and client side events are written in
-Javascript.
-
-The files from where these events are picked up are in the module folders in the
-repositories. Apart from the `core` module, all modules are parts
-of **erpnext** (`app` folder). Each DocType has its own folder in the module in a
-folder called `doctype`. If you browse the files of **erpnext**, you should be able
-to locate these files easily.
-
-#### Server-side modules
-
-For example, the server-side script for DocType **Account** in module **Accounts**
-will be present in the folder `app/accounts/doctype/account/account.py`
-
-The events are declared as a part of class called `DocType`. In the `DocType`
-class there are two main useful properties:
-
-- `doc`: Represents the main record.
-- `doclist`: Represents list of records (including child records) that are associated
-with this DocType. For example the `doclist` of **Sales Order** will have the main record
-and all **Sales Order Item** records.
-
-The main serverside events are:
-
-- `validate`: Called before the `INSERT` or `UPDATE` method is called.
-- `on_update`: Called after saving.
-- `on_submit`: Called after submission
-- `on_cancel`: Called after cancellation.
-
-See a sample server side file for more info!
-
----
-
-## Custom UI: Pages
-
-Custom UI like **Chart of Accounts** etc, is made by Pages. Pages are free form virtual
-pages in that are rendered on the client side. A page can have an `.html` (layout),
-`.py` (server calls), `.js` (user interface) and `.css` (style) components.
-
-Understand how pages work, it is best to open an existing page and see how it works.
-
----
-
-## Patching & Deployment
-
-Data / schema changes are done to wnframwork via patches released in the `app/patches`
-module (see erpnext folder for more details). To run all latest patches that have not
-been executed, run `lib/wnf.py -l`
-
-wnframework deployment is done by the `lib/wnf.py` utility.
-
-See `lib/wnf.py --help` for more help.
-
-_Good luck!_
diff --git a/wnf.py b/wnf.py
index ecc6e68281..de9248a246 100755
--- a/wnf.py
+++ b/wnf.py
@@ -125,8 +125,6 @@ def setup_utilities(parser):
help="Move site to different directory")
parser.add_argument("--with_files", default=False, action="store_true",
help="Also take backup of files")
- parser.add_argument("--docs", default=False, action="store_true",
- help="Build docs")
parser.add_argument("--domain", nargs="*",
help="Get or set domain in Website Settings")
parser.add_argument("--make_conf", nargs="*", metavar=("DB-NAME", "DB-PASSWORD"),
@@ -386,11 +384,6 @@ def move(site=None, dest_dir=None):
webnotes.destroy()
return os.path.basename(final_new_path)
-@cmd
-def docs():
- from core.doctype.documentation_tool.documentation_tool import write_static
- write_static()
-
@cmd
def domain(host_url=None, site=None):
webnotes.connect(site=site)