Esempio n. 1
0
		public Yield GetInfo(DreamContext aContext, DreamMessage aRequest, Result<DreamMessage> aResponse)
		{
			XDoc xmlInfo = new XDoc("info");
			xmlInfo.Elem("User", Context.Current.User);
			xmlInfo.Elem("About", "Foiremuses web service (c) 2011 Vincent DARON / Danny WILLEM");
			aResponse.Return(DreamMessage.Ok(MimeType.XML, xmlInfo));
			yield break;
		}
 //--- Class Methods ---
 private static void XmlRpcLiteralRecurse(XDoc xdoc, DekiScriptLiteral value, bool isArgumentList) {
     if(!isArgumentList) {
         xdoc.Start("value");
     }
     switch(value.ScriptType) {
     case DekiScriptType.BOOL:
         xdoc.Elem("boolean", ((DekiScriptBool)value).Value ? "1" : "0");
         break;
     case DekiScriptType.NUM:
         xdoc.Elem("double", ((DekiScriptNumber)value).Value);
         break;
     case DekiScriptType.STR:
         xdoc.Elem("string", ((DekiScriptString)value).Value); // in order to work with php, this may need to be encoded
         break;
     case DekiScriptType.NIL:
         xdoc.Elem("nil");
         break;
     case DekiScriptType.URI:
         xdoc.Start("string").Attr("type", "uri").End();
         break;
     case DekiScriptType.XML:
         xdoc.Start("string").Attr("type", "xml").Value(value.NativeValue.ToString()).End();
         break;
     case DekiScriptType.LIST:
         xdoc.Start(isArgumentList ? "params" : "array");
         if(!isArgumentList)
             xdoc.Start("data");
         foreach(DekiScriptLiteral entry in ((DekiScriptList)value).Value) {
             if(isArgumentList) {
                 xdoc.Start("param");
                 XmlRpcLiteralRecurse(xdoc, entry, false);
                 xdoc.End();
             } else {
                 XmlRpcLiteralRecurse(xdoc, entry, false);
             }
         }
         if(!isArgumentList)
             xdoc.End();
         xdoc.End();
         break;
     case DekiScriptType.MAP:
         xdoc.Start("struct");
         foreach(KeyValuePair<string, DekiScriptLiteral> entry in ((DekiScriptMap)value).Value) {
             xdoc.Start("member");
             xdoc.Elem("name", entry.Key);
             XmlRpcLiteralRecurse(xdoc, entry.Value, false);
             xdoc.End();
         }
         xdoc.End();
         break;
     default:
         throw new ShouldNeverHappenException("unkwown type");
     }
     if(!isArgumentList)
         xdoc.End();
     return;
 }
        public void TestFullServiceLifetime() {
            Plug p = Utils.BuildPlugForAdmin();

            string desc = "test service";

            XDoc serviceXml = new XDoc("service");
            serviceXml.Elem("sid", TEST_SERVICE_SID);
            serviceXml.Elem("type", "ext");
            serviceXml.Elem("description", desc);
            serviceXml.Elem("init", "native");

            //create the service
            DreamMessage msg = p.At("site", "services").PostAsync(serviceXml).Wait();
            Assert.IsTrue(msg.IsSuccessful, "service creation failed");
            uint service_id = msg.ToDocument()["@id"].AsUInt ?? 0;
            Assert.IsTrue(service_id > 0);
            
            //todo: validate the service

            //start the service
            msg = p.At("site", "services", service_id.ToString(), "start").PostAsync().Wait();
            Assert.IsTrue(msg.IsSuccessful, "service startup failed");
            XUri uri = msg.ToDocument()["uri"].AsUri;
            Assert.IsNotNull(uri);
            Assert.IsTrue(!string.IsNullOrEmpty(uri.ToString()));

            //stop the service
            msg = p.At("site", "services", service_id.ToString(), "stop").PostAsync().Wait();
            Assert.IsTrue(msg.IsSuccessful, "service stopping failed");
            Assert.IsTrue(string.IsNullOrEmpty(msg.ToDocument()["uri"].AsText));
            msg = p.At("site", "services", service_id.ToString()).GetAsync().Wait();
            Assert.IsTrue(msg.IsSuccessful);
            serviceXml = msg.ToDocument();

            //start the service
            msg = p.At("site", "services", service_id.ToString(), "start").PostAsync().Wait();
            Assert.IsTrue(msg.IsSuccessful, "service startup failed");
            uri = msg.ToDocument()["uri"].AsUri;
            Assert.IsNotNull(uri);
            Assert.IsTrue(!string.IsNullOrEmpty(uri.ToString()));

            //start the service
            msg = p.At("site", "services", service_id.ToString(), "start").PostAsync().Wait();
            Assert.IsTrue(msg.IsSuccessful, "service refresh failed");
            uri = msg.ToDocument()["uri"].AsUri;
            Assert.IsNotNull(uri);
            Assert.IsTrue(!string.IsNullOrEmpty(uri.ToString()));
        
            //delete the service
            msg = p.At("site", "services", service_id.ToString()).DeleteAsync().Wait();
            Assert.IsTrue(msg.IsSuccessful, "service deletion failed");        
            msg = p.At("site", "services", service_id.ToString()).GetAsync().Wait();
            Assert.AreEqual(DreamStatus.NotFound, msg.Status, "service still exists after deletion");
        }
Esempio n. 4
0
        //--- Class Methods ---
        private static XDoc AddTableStyles(XDoc doc) {
            XDoc head = doc["head"];
            if(head.IsEmpty) {
                doc.Elem("head");
                head = doc["head"];
            }
            head.Start("style").Attr("type", "text/css").Value(@".feedtable {
    border:1px solid #999;
    line-height:1.5em;
    overflow:hidden;
    width:100%;
}
.feedtable th {
    background-color:#ddd;
    border-bottom:1px solid #999;
    font-size:14px;
}
.feedtable tr {
    background-color:#FFFFFF;
}
.feedtable tr.feedroweven td {
    background-color:#ededed;
}").End();
            return doc;
        }
Esempio n. 5
0
 public void Can_provide_list_of_args_as_repeated_params_to_feature()
 {
     MockServiceInfo mock = MockService.CreateMockService(_hostInfo);
     mock.Service.CatchAllCallback = delegate(DreamContext context, DreamMessage request, Result<DreamMessage> response2) {
         XDoc msg = new XDoc("ids");
         foreach(KeyValuePair<string, string> kv in context.GetParams()) {
             if(kv.Key == "id") {
                 msg.Elem("id", kv.Value);
             }
         }
         response2.Return(DreamMessage.Ok(msg));
     };
     Plug p = mock.AtLocalHost;
     int n = 100;
     List<string> ids = new List<string>();
     for(int i = 0; i < n; i++) {
         p = p.With("id", i);
         ids.Add(i.ToString());
     }
     DreamMessage result = p.GetAsync().Wait();
     Assert.IsTrue(result.IsSuccessful);
     List<string> seen = new List<string>();
     foreach(XDoc id in result.ToDocument()["id"]) {
         string v = id.AsText;
         Assert.Contains(v, ids);
         Assert.IsFalse(seen.Contains(v));
         seen.Add(v);
     }
     Assert.AreEqual(ids.Count, seen.Count);
 }
        public Yield GetSearchDescription(DreamContext context, DreamMessage request, Result<DreamMessage> response) {
            XDoc description = new XDoc("OpenSearchDescription", "http://a9.com/-/spec/opensearch/1.1/");
            description.Elem("ShortName", string.Format(DekiResources.OPENSEARCH_SHORTNAME, DekiContext.Current.Instance.SiteName))
                       .Elem("Description", DekiResources.OPENSEARCH_DESCRIPTION)
                       .Start("Query")
                            .Attr("role", "example")
                            .Attr("searchTerms", "Wiki")
                       .End();

            // HACK HACK HACK: we can't use XUri because it encodes the "{}" characters
            string uri = DekiContext.Current.ApiUri.At("site", "opensearch").ToString();
            uri += "?q={searchTerms}&offset={startIndex}&limit={count?}&";

            description.Start("Url")
                 .Attr("type", "text/html")
                 .Attr("indexOffset", 0)
                 .Attr("template", DekiContext.Current.UiUri.At("Special:Search").ToString() + "?search={searchTerms}&offset=0&limit={count?}&format=html")
            .End()
            .Start("Url")
                 .Attr("type", "application/atom+xml")
                 .Attr("indexOffset", 0)
                 .Attr("template", uri + "format=atom")
            .End()
            .Start("Url")
                 .Attr("type", "application/rss+xml")
                 .Attr("indexOffset", 0)
                 .Attr("template", uri + "format=rss")
            .End()
            .Start("Url")
                 .Attr("type", "application/x-suggestions+json")
                 .Attr("template", DekiContext.Current.ApiUri.At("site", "opensearch", "suggestions").ToString() + "?q={searchTerms}")
             .End();
            response.Return(DreamMessage.Ok(description));
            yield break;
        }
 //--- Methods ---
 public XDoc ToXml(XUri uri) {
     XDoc result = new XDoc("function");
     result.Attr("transform", Transform);
     if(IsProperty) {
         result.Attr("usage", "property");
     }
     result.Elem("name", Name);
     result.Elem("uri", uri);
     result.Elem("description", Description);
     if(Access != DreamAccess.Public) {
         result.Elem("access", Access.ToString().ToLowerInvariant());
     }
     foreach(DekiScriptParameter param in Parameters) {
         param.AppendXml(result);
     }
     result.Start("return").Attr("type", DekiScriptLiteral.AsScriptTypeName(ReturnType)).End();
     return result;
 }
Esempio n. 8
0
 //--- Methods ---
 public XDoc ToXml() {
     XDoc result = new XDoc("group");
     result.Attr("name", Name);
     if(HasCustom) {
         foreach(KeyValuePair<string, string> custom in ArrayUtil.AllKeyValues(Custom)) {
             result.Elem(custom.Key, custom.Value);
         }
     }
     return result;
 }
Esempio n. 9
0
        //--- Class Methods ---
        private static void Main(string[] args) {

            Plug host = null;
            try {
                // create the dream environment
                XDoc dreamConfigDoc = new XDoc("config");
                dreamConfigDoc.Elem("server-name", MKS_PATH);
                dreamConfigDoc.Elem("service-dir", Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location));
                dreamConfigDoc.Elem("apikey", API_KEY);
                
                host = (new DreamHost(dreamConfigDoc)).Self.With("apikey", API_KEY);
                host.At("load").With("name", "mindtouch.deki.mwconverter").Post();
                host.At("load").With("name", "mindtouch.deki").Post();
                host.At("load").With("name", "mindtouch.indexservice").Post();
                host.At("load").With("name", "mindtouch.deki.services").Post();

            } catch (Exception e) {
                Console.WriteLine("An unexpected error occurred while creating the dream host.");
                Console.WriteLine(e);
                Environment.Exit(1);
            }

            try {

                // load the configuration information
                XDoc converterConfigDoc = XDocFactory.LoadFrom(CONFIG_FILE, MimeType.XML);
                XDoc dekiConfigDoc = XDocFactory.LoadFrom(converterConfigDoc["//deki/startup-xml"].Contents, MimeType.XML)["//config"];
                dekiConfigDoc["path"].ReplaceValue("converter");
                dekiConfigDoc["sid"].ReplaceValue("http://services.mindtouch.com/deki/internal/2007/12/mediawiki-converter");
                dekiConfigDoc.Add(converterConfigDoc["//mediawiki"]);
                host.At("services").Post(dekiConfigDoc);
            } catch (Exception e) {
                Console.WriteLine("An unexpected error occurred while loading the converter configuration settings.");
                Console.WriteLine(e);
                Environment.Exit(1);
            }
               

            Plug service = Plug.New(host.Uri.AtAbsolutePath("converter"), TimeSpan.MaxValue);
            service.PostAsync();
            Console.ReadLine();
        }
Esempio n. 10
0
        protected override XDoc GetConfigForWikiId(string wikiId) {
            string configXpath = string.Format("wikis/config[@id='{0}']", wikiId);
            XDoc instanceConfig = _dekiService.Config[configXpath];
            if (instanceConfig.IsEmpty && wikiId == DEFAULT_WIKI_ID && _dekiService.Config["wikis"].IsEmpty) {

                // For backwards compatibility with older style config doc, just extract the db settings from the service startup xml.
                // All other settings are either environmental(service-wide) or in the config table.
                instanceConfig = new XDoc("config");
                foreach (string s in new string[] { "db-server", "db-port", "db-catalog", "db-user", "db-password", "db-options" }) {
                    instanceConfig.Elem(s, _dekiService.Config[s].AsText);
                }
            }
            return instanceConfig;
        }
        public static XDoc DekiScriptToXmlRpc(string function, DekiScriptLiteral arguments)
        {
            XDoc xdoc = new XDoc("methodCall");

            xdoc.Elem("methodName", function);
            if (arguments.ScriptType.Equals(DekiScriptType.LIST))
            {
                XmlRpcLiteralRecurse(xdoc, arguments, true);
            }
            else
            {
                xdoc.Start("params").Start("param");
                XmlRpcLiteralRecurse(xdoc, arguments, false);
                xdoc.End().End();
            }
            return(xdoc);
        }
Esempio n. 12
0
        protected override XDoc GetConfigForWikiId(string wikiId)
        {
            string configXpath    = string.Format("wikis/config[@id='{0}']", wikiId);
            XDoc   instanceConfig = _dekiService.Config[configXpath];

            if (instanceConfig.IsEmpty && wikiId == DEFAULT_WIKI_ID && _dekiService.Config["wikis"].IsEmpty)
            {
                // For backwards compatibility with older style config doc, just extract the db settings from the service startup xml.
                // All other settings are either environmental(service-wide) or in the config table.
                instanceConfig = new XDoc("config");
                foreach (string s in new string[] { "db-server", "db-port", "db-catalog", "db-user", "db-password", "db-options" })
                {
                    instanceConfig.Elem(s, _dekiService.Config[s].AsText);
                }
            }
            return(instanceConfig);
        }
Esempio n. 13
0
        /// <summary>
        /// Execute command and read result into an XDoc.
        /// </summary>
        /// <param name="table">Name of the root element</param>
        /// <param name="row">Name of the element created for each row</param>
        /// <returns>Read DataSet object</returns>
        public XDoc ReadAsXDoc(string table, string row)
        {
            _log.TraceMethodCall("ReadAsXDoc()", _command.CommandText);
            XDoc result = new XDoc(table);

            Execute(delegate(IDataReader reader) {
                // capture row columns
                int count        = reader.FieldCount;
                string[] columns = new string[count];
                bool[] attr      = new bool[count];
                for (int i = 0; i < count; ++i)
                {
                    columns[i] = reader.GetName(i);
                    if (columns[i].StartsWith("@"))
                    {
                        attr[i]    = true;
                        columns[i] = columns[i].Substring(1);
                    }
                }

                // read records
                while (reader.Read())
                {
                    result.Start(row);
                    for (int i = 0; i < count; ++i)
                    {
                        if (!reader.IsDBNull(i))
                        {
                            string column = columns[i];
                            if (attr[0])
                            {
                                result.Attr(column, reader.GetValue(i).ToString());
                            }
                            else
                            {
                                result.Elem(column, reader.GetValue(i).ToString());
                            }
                        }
                    }
                    result.End();
                }
            });
            return(result);
        }
Esempio n. 14
0
        public static XDoc GetUserMetricsXml(UserBE user)
        {
            var metrics = DbUtils.CurrentSession.Users_GetUserMetrics(user.ID);
            var ret     = new XDoc("metrics");

            ret.Attr("user.id", user.ID);
            ret.Attr("href", DekiContext.Current.ApiUri.At("users", user.ID.ToString(), "metrics"));
            ret.Elem("metric.comments", metrics.CommentPosts);
            ret.Elem("metric.pages-created", metrics.PagesCreated);
            ret.Elem("metric.pages-edited", metrics.PagesChanged);
            ret.Elem("metric.files-added", metrics.FilesUploaded);
            ret.Elem("metric.ratings-up", metrics.UpRatings);
            ret.Elem("metric.ratings-down", metrics.DownRatings);
            return(ret);
        }
Esempio n. 15
0
        public Yield PostRun(DreamContext context, DreamMessage request, Result <DreamMessage> response)
        {
            XDoc   doc   = request.ToDocument();
            string name  = doc["dappName"].AsText;
            XUri   input = doc["applyToUrl"].AsUri;
            string xpath = doc["xpath"].AsText;

            // convert args
            Hashtable args = new Hashtable();

            foreach (XDoc item in doc.Elements)
            {
                if (StringUtil.StartsWithInvariant(item.Name, VARIABLE_PREFIX))
                {
                    args[item.Name.Substring(VARIABLE_PREFIX.Length)] = item.AsText;
                }
            }

            // invoke dapper
            Result <XDoc> res;

            yield return(res = Coroutine.Invoke(FetchResult, name, input, args, new Result <XDoc>()));

            // create result document
            XDoc rows   = res.Value[xpath ?? ".//*[@type='group']"];
            XDoc result = new XDoc("results");

            foreach (XDoc row in rows)
            {
                result.Start("result");
                foreach (XDoc cell in row.Elements)
                {
                    result.Elem(cell.Name, cell.AsText);
                }
                result.End();
            }
            string json = JsonUtil.ToJson(result);

            response.Return(DreamMessage.Ok(MimeType.JSON, json));
            yield break;
        }
Esempio n. 16
0
        /// <summary>
        /// Builds a http://sitemaps.org compliant sitemap as used by google (https://www.google.com/webmasters/tools/docs/en/protocol.html)
        /// </summary>
        /// <param name="rootPage"></param>
        /// <returns></returns>
        public static XDoc BuildGoogleSiteMap(PageBE rootPage, string language)
        {
            IList <PageBE> pages = null;
            Dictionary <ulong, IList <ulong> > childrenInfo = null;

            DbUtils.CurrentSession.Pages_GetDescendants(rootPage, null, true, out pages, out childrenInfo, ConfigBL.GetInstanceSettingsValueAs <int>(ConfigBL.MAX_SITEMAP_SIZE_KEY, ConfigBL.MAX_SITEMAP_SIZE));

            PageBE[] allowedPages = PermissionsBL.FilterDisallowed(DekiContext.Current.User, pages, false, new Permissions[] { Permissions.BROWSE });
            Dictionary <ulong, PageBE> allowedPagesById = allowedPages.AsHash(e => e.ID);
            Dictionary <ulong, PageBE> addedPagesById   = null;

            if (!string.IsNullOrEmpty(language))
            {
                List <ulong> pagesToRemove = new List <ulong>();
                foreach (KeyValuePair <ulong, PageBE> page in allowedPagesById)
                {
                    if (!string.IsNullOrEmpty(page.Value.Language) && !StringUtil.EqualsInvariantIgnoreCase(page.Value.Language, language))
                    {
                        pagesToRemove.Add(page.Key);
                    }
                }
                foreach (ulong pageId in pagesToRemove)
                {
                    allowedPagesById.Remove(pageId);
                }
            }
            PageBL.AddParentsOfAllowedChildren(rootPage, allowedPagesById, addedPagesById);

            XDoc x = new XDoc("urlset", "http://www.google.com/schemas/sitemap/0.84");

            foreach (PageBE p in allowedPagesById.Values)
            {
                x.Start("url");
                x.Elem("loc", Utils.AsPublicUiUri(p.Title));
                x.Start("lastmod").Value(p.TimeStamp.ToString("yyyy-MM-dd")).End();
                x.End();
            }

            return(x);
        }
Esempio n. 17
0
        public void Can_provide_list_of_args_as_repeated_params_to_feature()
        {
            MockServiceInfo mock = MockService.CreateMockService(_hostInfo);

            mock.Service.CatchAllCallback = delegate(DreamContext context, DreamMessage request, Result <DreamMessage> response2) {
                XDoc msg = new XDoc("ids");
                foreach (KeyValuePair <string, string> kv in context.GetParams())
                {
                    if (kv.Key == "id")
                    {
                        msg.Elem("id", kv.Value);
                    }
                }
                response2.Return(DreamMessage.Ok(msg));
            };
            Plug          p   = mock.AtLocalHost;
            int           n   = 100;
            List <string> ids = new List <string>();

            for (int i = 0; i < n; i++)
            {
                p = p.With("id", i);
                ids.Add(i.ToString());
            }
            DreamMessage result = p.GetAsync().Wait();

            Assert.IsTrue(result.IsSuccessful);
            List <string> seen = new List <string>();

            foreach (XDoc id in result.ToDocument()["id"])
            {
                string v = id.AsText;
                Assert.Contains(v, ids);
                Assert.IsFalse(seen.Contains(v));
                seen.Add(v);
            }
            Assert.AreEqual(ids.Count, seen.Count);
        }
Esempio n. 18
0
        public static DreamMessage BuildDeletedPageContents(uint pageid) {
            ArchiveBE page = DbUtils.CurrentSession.Archive_GetPageHeadById(pageid);
            if (page == null) {
                throw new DreamAbortException(DreamMessage.NotFound(string.Format(DekiResources.RESTORE_PAGE_ID_NOT_FOUND, pageid)));
            }

            //HACKHACKHACK MaxM: Copy data to a PageBE object since parser will not work on an ArchiveBE. ArchiveBE needs to go away.
            PageBE tempP = new PageBE();
            tempP.Title = page.Title;
            tempP.SetText(page.Text);
            tempP.ContentType = page.ContentType;

            ParserResult parserResult = DekiXmlParser.Parse(tempP, ParserMode.VIEW_NO_EXECUTE);

            // TODO (steveb): this code is almost identical to the one in "GET:pages/{pageid}/contents"; consider merging

            // post process tail
            DekiXmlParser.PostProcessParserResults(parserResult);

            // wrap the result in a content tag and return it to the user
            XDoc result = new XDoc("content").Attr("type", parserResult.ContentType);
            foreach (XDoc entry in parserResult.Content.Elements) {
                if (entry.HasName("body")) {
                    result.Start("body").Attr("target", entry["@target"].AsText).Value(entry.ToInnerXHtml()).End();
                } else {
                    result.Elem(entry.Name, entry.ToInnerXHtml());
                }
            }
            // check if we hit a snag, which is indicated by a plain-text response
            if ((parserResult.ContentType == MimeType.TEXT.FullType) && (page.ContentType != MimeType.TEXT.FullType)) {

                // something happened during parsing
                return new DreamMessage(DreamStatus.NonAuthoritativeInformation, null, result);
            } else {
                return DreamMessage.Ok(result);
            }
        }
Esempio n. 19
0
        private Yield ConfigureMailer(XDoc settings, Result result)
        {
            var  instance = DekiContext.Current.Instance;
            XDoc config   = null;

            if (!string.IsNullOrEmpty(settings["mail/smtp-servers"].AsText))
            {
                var port = settings["mail/smtp-port"].AsText;
                config = new XDoc("smtp")
                         .Elem("smtp-host", settings["mail/smtp-servers"].AsText)
                         .Elem("use-ssl", (settings["mail/smtp-secure"].AsText ?? string.Empty).EndsWithInvariantIgnoreCase("ssl") || (settings["mail/smtp-secure"].AsText ?? string.Empty).EndsWithInvariantIgnoreCase("tls"))
                         .Elem("smtp-port", string.IsNullOrEmpty(port) ? null : port)
                         .Elem("smtp-auth-user", settings["mail/smtp-username"].AsText)
                         .Elem("smtp-auth-password", settings["mail/smtp-password"].AsText);
                if (!string.IsNullOrEmpty(instance.ApiKey))
                {
                    config.Elem("apikey", instance.ApiKey);
                }
            }
            if (config == null && !string.IsNullOrEmpty(instance.ApiKey))
            {
                config = new XDoc("config")
                         .Elem("apikey", instance.ApiKey)
                         .AddAll(Config["smtp/*"]);
            }
            if (config == null)
            {
                yield return(Mailer.At("configuration", instance.Id).DeleteAsync());
            }
            else
            {
                yield return(Mailer.At("configuration", instance.Id).PutAsync(config));
            }
            result.Return();
            yield break;
        }
 public void ToXml(XDoc parent)
 {
     parent
     .Start("function")
     .Elem("name", Name);
     if (!string.IsNullOrEmpty(_access))
     {
         parent.Elem("access", _access);
     }
     foreach (var parameter in _parameters)
     {
         parent
         .Start("param")
         .Attr("name", parameter.Key)
         .Attr("type", parameter.Value.Type);
         if (!string.IsNullOrEmpty(parameter.Value.Default))
         {
             parent.Attr("default", parameter.Value.Default);
         }
         parent.End();
     }
     parent
     .Start("return")
     .Attr("type", _type);
     if (_htmlBody != null)
     {
         parent.AddAll(_htmlBody);
     }
     else
     {
         parent.Value(_body);
     }
     parent
     .End()
     .End();
 }
Esempio n. 21
0
        public Yield GetExtensionLibrary(DreamContext contex, DreamMessage request, Result <DreamMessage> response)
        {
            // create manifest
            XDoc manifest = new XDoc("extension");

            manifest.Elem("title", _title);
            manifest.Elem("label", _label);
            manifest.Elem("copyright", _copyright);
            manifest.Elem("description", _description);
            manifest.Elem("uri.help", _help);
            manifest.Elem("uri.logo", _logo);
            manifest.Elem("namespace", _namespace);

            // add functions
            foreach (var function in _functions)
            {
                if (function.Value.Access == DreamAccess.Public)
                {
                    manifest.Add(function.Value.ToXml(function.Key));
                }
            }
            response.Return(DreamMessage.Ok(manifest));
            yield break;
        }
Esempio n. 22
0
        protected override Yield Start(XDoc config, IContainer container, Result result)
        {
            yield return(Coroutine.Invoke(base.Start, config, new Result()));

            // ensure imagemagick is setup correctly.
            if (string.IsNullOrEmpty(ImageMagickConvertPath))
            {
                throw new NotImplementedException("Please set 'imagemagick-convert-path' in config to path of ImageMagick's 'convert'");
            }
            if (!File.Exists(ImageMagickIdentifyPath))
            {
                throw new FileNotFoundException("Cannot find ImagicMagick 'identify' binary: ", ImageMagickIdentifyPath);
            }
            if (string.IsNullOrEmpty(ImageMagickIdentifyPath))
            {
                throw new NotImplementedException("Please set 'imagemagick-identify-path' in config to path of ImageMagick's 'identify'");
            }
            if (!File.Exists(ImageMagickConvertPath))
            {
                throw new FileNotFoundException("Cannot find ImagicMagick 'convert' binary: ", ImageMagickConvertPath);
            }

            // check for 'apikey'
            _apikey = Config["api-key"].AsText ?? Config["apikey"].AsText;
            if (string.IsNullOrEmpty(_apikey))
            {
                throw new ArgumentNullException("apikey", "The global apikey is not defined. Please ensure that you have a global <apikey> defined in the MindTouch Core service settings xml file.");
            }
            InitializeContainer(container);

            // intialize instance manager
            _instanceManager = InstanceManager.New(this, this.TimerFactory);

            // setup resource manager
            lock (SyncRoot) {
                if (ResourceManager == null)
                {
                    ResourceManager = new PlainTextResourceManager(ResourcesPath);
                    ScreenFont      = new DekiFont(Plug.New("resource://mindtouch.deki/MindTouch.Deki.Resources.Arial.mtdf").Get().AsBytes());
                }
            }

            // initialize scripting engine
            XDoc scripting = Config["scripting"];

            DekiScriptLibrary.InsertTextLimit = scripting["max-web-response-length"].AsLong ?? DekiScriptLibrary.InsertTextLimit;
            DekiScriptLibrary.MinCacheTtl     = scripting["min-web-cache-ttl"].AsDouble ?? DekiScriptLibrary.MinCacheTtl;

            // set up deki pub sub (by default we override uri.publish with our own service, unless @must-use=true is specified)
            if (!(Config["uri.publish/@must-use"].AsBool ?? false))
            {
                Result <Plug> pubsubResult;
                XDoc          pubsubConfig = new XDoc("config")
                                             .Elem("uri.deki", Self.Uri.With("apikey", MasterApiKey))
                                             .Start("downstream")
                                             .Elem("uri", PubSub.At("publish").Uri.WithoutLastSegment().At("subscribers"))
                                             .End()
                                             .Start("components")
                                             .Start("component")
                                             .Attr("type", typeof(IPubSubDispatcher).AssemblyQualifiedName)
                                             .Attr("implementation", typeof(DekiDispatcher).AssemblyQualifiedName)
                                             .End()
                                             .End()
                                             .Elem("authtoken", MasterApiKey);
                foreach (var cookie in Cookies.Fetch(PubSub.Uri))
                {
                    pubsubConfig.Add(cookie.AsSetCookieDocument);
                }
                var messageQueuePath = config["publish/queue-path"].AsText;
                if (!string.IsNullOrEmpty(messageQueuePath))
                {
                    pubsubConfig.Elem("queue-path", messageQueuePath);
                }
                yield return(pubsubResult = CreateService(
                                 "pubsub",
                                 "sid://mindtouch.com/dream/2008/10/pubsub",
                                 pubsubConfig,
                                 new Result <Plug>()));

                PubSub = pubsubResult.Value;
            }

            // set up package updater service (unless it was passed in)
            XUri packageUpdater;

            if (config["packageupdater/@uri"].IsEmpty)
            {
                var packageConfig = config["packageupdater"];
                packageConfig = packageConfig.IsEmpty ? new XDoc("config") : packageConfig.Clone();
                if (packageConfig["package-path"].IsEmpty)
                {
                    packageConfig.Elem("package-path", Path.Combine(Path.Combine(config["deki-path"].AsText, "packages"), "default"));
                }
                yield return(CreateService(
                                 "packageupdater",
                                 "sid://mindtouch.com/2010/04/packageupdater",
                                 new XDoc("config")
                                 .Elem("apikey", MasterApiKey)
                                 .AddNodes(packageConfig),
                                 new Result <Plug>()
                                 ));

                packageUpdater = Self.Uri.At("packageupdater");
            }
            else
            {
                packageUpdater = config["packageupdater/@uri"].AsUri;
            }
            _packageUpdater = Plug.New(packageUpdater);

            // set up emailer service (unless it was passed in)
            XUri mailerUri;

            if (config["uri.mailer"].IsEmpty)
            {
                yield return(CreateService(
                                 "mailer",
                                 "sid://mindtouch.com/2009/01/dream/email",
                                 new XDoc("config")
                                 .Elem("apikey", MasterApiKey)
                                 .AddAll(Config["smtp/*"]),
                                 new Result <Plug>()
                                 ));

                mailerUri = Self.Uri.At("mailer");
            }
            else
            {
                mailerUri = config["uri.mailer"].AsUri;
            }
            _mailer = Plug.New(mailerUri);

            // set up the email subscription service (unless it was passed in)
            XUri pageSubscription;

            if (config["uri.page-subscription"].IsEmpty)
            {
                XDoc pagesubserviceConfig = new XDoc("config")
                                            .Elem("uri.deki", Self.Uri)
                                            .Elem("uri.emailer", mailerUri.At("message"))
                                            .Elem("resources-path", ResourcesPath)
                                            .Elem("apikey", MasterApiKey)
                                            .Start("components")
                                            .Start("component")
                                            .Attr("scope", "factory")
                                            .Attr("type", typeof(IPageSubscriptionDataSessionFactory).AssemblyQualifiedName)
                                            .Attr("implementation", "MindTouch.Deki.Data.MySql.UserSubscription.MySqlPageSubscriptionSessionFactory, mindtouch.deki.data.mysql")
                                            .End()
                                            .End()
                                            .AddAll(Config["page-subscription/*"]);
                foreach (var cookie in Cookies.Fetch(mailerUri))
                {
                    pagesubserviceConfig.Add(cookie.AsSetCookieDocument);
                }
                yield return(CreateService(
                                 "pagesubservice",
                                 "sid://mindtouch.com/deki/2008/11/changesubscription",
                                 pagesubserviceConfig,
                                 new Result <Plug>()
                                 ));

                pageSubscription = Self.Uri.At("pagesubservice");
                config.Elem("uri.page-subscription", pageSubscription);
            }
            else
            {
                pageSubscription = config["uri.page-subscription"].AsUri;
            }
            _pageSubscription = Plug.New(pageSubscription);

            // set up package importer, if not provided
            if (Config["uri.package"].IsEmpty)
            {
                yield return(CreateService(
                                 "package",
                                 "sid://mindtouch.com/2009/07/package",
                                 new XDoc("config").Elem("uri.deki", Self.Uri),
                                 new Result <Plug>()));

                Config.Elem("uri.package", Self.Uri.At("package"));
            }

            // set up lucene
            _luceneIndex = Plug.New(Config["indexer/@src"].AsUri);
            if (_luceneIndex == null)
            {
                // create the indexer service
                XDoc luceneIndexConfig = new XDoc("config")
                                         .AddNodes(Config["indexer"])
                                         .Start("apikey").Attr("hidden", true).Value(MasterApiKey).End();
                if (luceneIndexConfig["path.store"].IsEmpty)
                {
                    luceneIndexConfig.Elem("path.store", Path.Combine(Path.Combine(config["deki-path"].AsText, "luceneindex"), "$1"));
                }
                yield return(CreateService("luceneindex", SID_FOR_LUCENE_INDEX, luceneIndexConfig, new Result <Plug>()).Set(v => _luceneIndex = v));

                _isLocalLuceneService = true;
            }
            else
            {
                // push our host's pubsub service to lucene, to keep it up to date on our changes
                var pubsub = new XDoc("pubsub").Attr("href", PubSub);
                foreach (var cookie in PubSub.CookieJar.Fetch(PubSub.Uri))
                {
                    pubsub.Add(cookie.AsSetCookieDocument);
                }
                yield return(_luceneIndex.At("subscriptions").PostAsync(pubsub));
            }

            // configure indexing whitelist
            _indexNamespaceWhitelist = new[] { NS.MAIN, NS.PROJECT, NS.USER, NS.TEMPLATE, NS.HELP, NS.MAIN_TALK, NS.PROJECT_TALK, NS.USER_TALK, NS.TEMPLATE_TALK, NS.HELP_TALK, NS.SPECIAL, NS.SPECIAL_TALK };
            if (!string.IsNullOrEmpty(Config["indexer/namespace-whitelist"].AsText))
            {
                List <NS> customWhitelist = new List <NS>();
                foreach (string item in Config["indexer/namespace-whitelist"].AsText.Split(','))
                {
                    NS ns;
                    if (SysUtil.TryParseEnum(item, out ns))
                    {
                        customWhitelist.Add(ns);
                    }
                }
                _indexNamespaceWhitelist = customWhitelist.ToArray();
            }

            if (!Config["wikis/globalconfig/cache/varnish"].IsEmpty)
            {
                // create the varnish service

                // TODO (petee): getting the varnish config from wikis/globalconfig/cache is a hack
                // The frontend needs to get the max-age to send out the cache headers but we currently have no way
                // of getting the DekiWikiService config so we'll hack it so it comes back in GET:site/settings.
                XDoc varnishConfig = new XDoc("config")
                                     .Elem("uri.deki", Self.Uri.With("apikey", MasterApiKey))
                                     .Elem("uri.varnish", Config["wikis/globalconfig/cache/varnish"].AsUri)
                                     .Elem("varnish-purge-delay", Config["wikis/globalconfig/cache/varnish-purge-delay"].AsInt ?? 10)
                                     .Elem("varnish-max-age", Config["wikis/globalconfig/cache/varnish-max-age"].AsInt ?? 300)
                                     .Start("apikey").Attr("hidden", true).Value(MasterApiKey).End();
                yield return(CreateService("varnish", SID_FOR_VARNISH_SERVICE, varnishConfig, new Result <Plug>()));
            }
            _isInitialized = true;
            result.Return();
        }
Esempio n. 23
0
        public Yield GetSiteFunctions(DreamContext context, DreamMessage request, Result <DreamMessage> response)
        {
            if (UserBL.IsAnonymous(DekiContext.Current.User))
            {
                throw new SiteMustBeLoggedInForbiddenException();
            }

            // build set of libraries
            List <XDoc> libraries = DekiContext.Current.Instance.RunningServices.ExtensionServices
                                    .Select(x => x.Extension.Manifest).ToList();

            // add registered libraries
            libraries.Sort((left, right) => left["title"].Contents.CompareInvariantIgnoreCase(right["title"].Contents));

            // add built-in functions
            XDoc builtinlib = new XDoc("extension");

            builtinlib.Elem("title", "Built-in Functions");
            builtinlib.Elem("label", "Built-in");
            builtinlib.Elem("uri.help", "http://wiki.developer.mindtouch.com/MindTouch_Deki/DekiScript/Reference");
            builtinlib.Elem("description", "The following functions and variables are part the DekiScript and MindTouch runtime environment.");
            foreach (var function in ScriptRuntime.Functions.Values)
            {
                if (function.Access == DreamAccess.Public)
                {
                    builtinlib.Add(function.ToXml(null));
                }
            }
            libraries.Insert(0, builtinlib);

            // create composite document
            bool hasUnsafeContentPermission = PermissionsBL.IsUserAllowed(DekiContext.Current.User, Permissions.UNSAFECONTENT);
            XDoc extensions = new XDoc("extensions").AddAll(libraries);

            foreach (XDoc extension in extensions["extension"])
            {
                XUri serviceUri = extension["@uri"].AsUri;

                // check if extension is protected
                bool @protected;
                bool.TryParse(ExtensionBL.GetExtensionPreference(serviceUri, "protected"), out @protected);
                if (@protected)
                {
                    if (!hasUnsafeContentPermission)
                    {
                        extension.Remove();
                        continue;
                    }
                    extension.Attr("protected", @protected);
                }

                // read overwriteable settings
                AddOrReplace(extension, "title", ExtensionBL.GetExtensionPreference(serviceUri, "title.custom"));
                AddOrReplace(extension, "label", ExtensionBL.GetExtensionPreference(serviceUri, "label.custom"));
                AddOrReplace(extension, "uri.logo", ExtensionBL.GetExtensionPreference(serviceUri, "uri.logo.custom"));
                AddOrReplace(extension, "namespace", ExtensionBL.GetExtensionPreference(serviceUri, "namespace.custom"));
                extension.Elem("description.custom", ExtensionBL.GetExtensionPreference(serviceUri, "description.custom"));

                // check which functions to keep
                string[] allowedFunctions = (ExtensionBL.GetExtensionPreference(serviceUri, "functions") ?? string.Empty).Split(new char[] { ' ', ',' }, StringSplitOptions.RemoveEmptyEntries);
                if (allowedFunctions.Length > 0)
                {
                    foreach (XDoc function in extension["function"])
                    {
                        // check if user specified a list of functions to show
                        string name = function["name"].Contents;
                        if (Array.FindIndex(allowedFunctions, current => current.EqualsInvariantIgnoreCase(name)) < 0)
                        {
                            function.Remove();
                        }
                    }
                }

                // check if extension has any functions
                if (extension["function"].ListLength == 0)
                {
                    extension.Remove();
                }
            }

            // build response document
            string format = context.GetParam("format", "html");

            if (StringUtil.EqualsInvariant(format, "xml"))
            {
                response.Return(DreamMessage.Ok(extensions));
            }
            else
            {
                // prepare document
                string header = string.Format("{0} - Registered Extensions", DekiContext.Current.Instance.SiteName);
                XDoc   result = new XDoc("html").Attr("xmlns", "http://www.w3.org/1999/xhtml")
                                .Start("head")
                                .Elem("title", header)
                                .Start("meta").Attr("http-equiv", "content-type").Attr("content", "text/html;charset=utf-8").End()
                                .End();
                result.Start("body");
                result.Elem("h1", header);

                // build table of contents
                result.Elem("strong", "Table of Contents");
                result.Start("ol");
                int count = 0;
                foreach (XDoc library in extensions["extension"])
                {
                    ++count;
                    XUri serviceUri = library["@uri"].AsUri;
                    result.Start("li")
                    .Start("a")
                    .Attr("href", "#section" + count)
                    .Value(ExtensionBL.GetExtensionPreference(serviceUri, "title.custom") ?? library["title"].AsText)
                    .End()
                    .End();
                }
                result.End();

                // enumerate libraries
                count = 0;
                foreach (XDoc library in extensions["extension"])
                {
                    ++count;

                    // read overwriteable settings
                    string title      = library["title"].AsText;
                    string logo       = library["uri.logo"].AsText;
                    string ns         = library["namespace"].AsText;
                    bool   @protected = library["@protected"].AsBool ?? false;

                    // show & link library name
                    result.Start("h2").Attr("id", "section" + count);
                    if (!string.IsNullOrEmpty(library["uri.help"].AsText))
                    {
                        result.Start("a").Attr("href", library["uri.help"].AsText).Attr("target", "_blank").Attr("title", library["title"].AsText + " Documentation").Value(title).End();
                    }
                    else
                    {
                        result.Value(title);
                    }
                    if (@protected)
                    {
                        var resources = DekiContext.Current.Resources;
                        var builder   = new DekiResourceBuilder();
                        builder.Append(" (");
                        builder.Append(DekiResources.PROTECTED());
                        builder.Append(")");
                        result.Value(builder.Localize(resources));
                    }
                    result.End();

                    // show optional logo
                    if (!string.IsNullOrEmpty(logo))
                    {
                        result.Start("img").Attr("src", logo).Attr("alt", title).End();
                    }

                    // show descriptions
                    if (library["uri.license"].AsText != null)
                    {
                        result.Start("a").Attr("href", library["uri.license"].AsText).Attr("target", "_blank").Value("Read Library License").End();
                    }
                    if (!string.IsNullOrEmpty(library["description"].AsText))
                    {
                        result.Elem("p", library["description"].AsText);
                    }
                    if (!string.IsNullOrEmpty(library["description.custom"].AsText))
                    {
                        result.Elem("p", library["description.custom"].AsText);
                    }

                    // enumerate library functions
                    XDoc functions = new XDoc("functions").AddAll(library["function"]);
                    functions.Sort(delegate(XDoc left, XDoc right) {
                        return(StringUtil.CompareInvariantIgnoreCase(left["name"].Contents, right["name"].Contents));
                    });
                    foreach (XDoc function in functions["function"])
                    {
                        AddFunction(result, ns, function);
                    }
                }
                result.End();
                switch (format)
                {
                default:
                case "html":
                    response.Return(DreamMessage.Ok(MimeType.HTML, result.ToString()));
                    break;

                case "body":
                    response.Return(DreamMessage.Ok(MimeType.TEXT_UTF8, result["body"].Contents));
                    break;
                }
            }
            yield break;
        }
Esempio n. 24
0
        public void TestPutSiteServiceId() {
            Plug p = Utils.BuildPlugForAdmin();
            XDoc serviceXml = new XDoc("service");
            serviceXml.Elem("sid", TEST_SERVICE_SID);
            serviceXml.Elem("type", "ext");
            serviceXml.Elem("description", "test1");
            serviceXml.Elem("init", "native");
            serviceXml.Start("config");
            serviceXml.Start("value").Attr("key", "keyfoo1").Value("valbar1").End();
            serviceXml.Start("value").Attr("key", "keyfoo2").Value("valbar2").End();
            serviceXml.End();

            //create the service
            DreamMessage msg = p.At("site", "services").PostAsync(serviceXml).Wait();
            Assert.IsTrue(msg.IsSuccessful, "service creation failed");
            uint service_id = msg.ToDocument()["@id"].AsUInt ?? 0;
            Assert.IsTrue(service_id > 0);
            serviceXml = msg.ToDocument();
            Assert.IsTrue(msg.ToDocument()["description"].AsText == "test1");
            Assert.IsTrue(msg.ToDocument()["config/value[@key = 'keyfoo1']"].AsText == "valbar1");
            Assert.IsTrue(msg.ToDocument()["config/value[@key = 'keyfoo2']"].AsText == "valbar2");

            //edit the service
            serviceXml["description"].Remove();
            serviceXml["config/value[@key = 'keyfoo2']"].Remove();
            serviceXml["config/value[@key = 'keyfoo1']"].Remove();
            serviceXml["config"].Start("value").Attr("key", "keyfoo1new").Value("valbar1new").End();
            serviceXml["config"].Start("value").Attr("key", "keyfoo2new").Value("valbar2new").End();
            serviceXml.Elem("description", "test2");
            msg = p.At("site", "services", service_id.ToString()).PutAsync(serviceXml).Wait();
            Assert.IsTrue(msg.IsSuccessful, "service editing failed");

            //validate edit
            msg = p.At("site", "services", service_id.ToString()).GetAsync().Wait();
            Assert.IsTrue(msg.IsSuccessful);
            Assert.IsTrue(msg.ToDocument()["description"].AsText == "test2");
            Assert.IsTrue(msg.ToDocument()["config/value[@key = 'keyfoo1new']"].AsText == "valbar1new");
            Assert.IsTrue(msg.ToDocument()["config/value[@key = 'keyfoo2new']"].AsText == "valbar2new");
            Assert.IsTrue(msg.ToDocument()["config/value[@key = 'keyfoo1']"].AsText == null);
            Assert.IsTrue(msg.ToDocument()["config/value[@key = 'keyfoo2']"].AsText == null);

            //delete the service
            msg = p.At("site", "services", service_id.ToString()).DeleteAsync().Wait();
            Assert.IsTrue(msg.IsSuccessful, "service deletion failed");
            msg = p.At("site", "services", service_id.ToString()).GetAsync().Wait();
            Assert.IsTrue(msg.Status == DreamStatus.NotFound, "service still exists after deletion");
        }
Esempio n. 25
0
        //--- Class Methods ---
        public static ServiceBE StartService(ServiceBE service, bool forceRefresh, bool disableOnFailure) {
           
            // create subordinate request id for service start
            var dreamContext = DreamContext.Current;
            var requestId = dreamContext.GetState<string>(DreamHeaders.DREAM_REQUEST_ID);
            dreamContext.SetState(DreamHeaders.DREAM_REQUEST_ID, requestId + "-service_" + service.Id);

            try {
                Stopwatch stopwatch = new Stopwatch();
                stopwatch.Start();
                service.ServiceLastStatus = string.Empty;
                StopService(service.Id, service, ServiceStopType.Restart);
                DekiContext context = DekiContext.Current;
                bool dirtyServiceEntity = false;
                XUri location;
                ServiceRepository.IServiceInfo serviceInfo = null;
                try {

                    // check if service is local
                    if(service.ServiceLocal) {
                        if(string.IsNullOrEmpty(service.SID)) {
                            throw new Exception("missing SID");
                        }

                        // start service
                        if(IsLocalAuthService(service)) {

                            // this service is the built-in authentication provider; no need to start it
                            location = context.Deki.Self;
                        } else {

                            // convert local service configuration into an xdoc
                            XDoc config = new XDoc("config");
                            foreach(KeyValuePair<string, string> configEntry in ArrayUtil.AllKeyValues(service.Config)) {
                                config.InsertValueAt(configEntry.Key, configEntry.Value);
                            }

                            // if no apikey was provided, create a random one so that CreateService doesn't inject the parent one
                            if(config["apikey"].IsEmpty) {
                                config.Elem("apikey", StringUtil.CreateAlphaNumericKey(16));
                            }

                            // add information for service to callback into deki
                            if(config["uri.deki"].IsEmpty) {
                                config.Elem("uri.deki", context.Deki.Self);
                                config.Elem("wikiid.deki", context.Instance.Id);
                                config.Elem("apikey.deki", context.Deki.MasterApiKey);
                            }

                            // the service location must use the service ID and the instance ID
                            string servicePath = string.Format("services/{0}/{1}", context.Instance.Id, service.Id);
                            serviceInfo = context.Instance.CreateLocalService(service, servicePath, config);
                            location = serviceInfo.ServiceUri;
                        }

                        // check if the service uri has changed since last invocation (happens when service is started for the first time or server GUID has changed)
                        if(!service.Uri.EqualsInvariantIgnoreCase(location.ToString())) {
                            dirtyServiceEntity = true;
                            service.Uri = location.ToString();
                        }
                    } else {
                        if(string.IsNullOrEmpty(service.Uri)) {
                            throw new Exception("missing URI");
                        }
                        location = new XUri(service.Uri);
                        serviceInfo = context.Instance.RegisterRemoteService(service, location);
                    }

                    // check if service is an Extension service
                    if(service.Type == ServiceType.EXT) {
                        ExtensionBL.StartExtensionService(context, service, serviceInfo, forceRefresh);
                    }

                    //Successfully starting a service enables it.
                    if(!service.ServiceEnabled) {
                        dirtyServiceEntity = true;
                        service.ServiceEnabled = true;
                    }
                } catch(Exception e) {
                    dirtyServiceEntity = true;
                    DreamMessage dm = null;
                    if(e is DreamResponseException) {
                        dm = ((DreamResponseException)e).Response;
                        string message = dm.HasDocument ? dm.ToDocument()[".//message"].AsText.IfNullOrEmpty(e.Message) : dm.ToText();
                        service.ServiceLastStatus = string.Format("unable to initialize service ({0})", message);
                    } else {
                        service.ServiceLastStatus = e.GetCoroutineStackTrace();
                    }
                    if(serviceInfo != null) {
                        try {
                            context.Instance.DeregisterService(service.Id);
                        } catch {}
                    }

                    // A service that fails to start becomes disabled if it's started explicitly (not during deki startup)
                    if(disableOnFailure) {
                        service.ServiceEnabled = false;
                    }

                    context.Instance.Log.ErrorExceptionMethodCall(e, "StartService", string.Format("Unable to start local service id '{0}' with SID '{1}' Error: '{2}'", service.Id, service.SID, service.ServiceLastStatus));
                    if(dm != null) {
                        throw new DreamAbortException(dm);
                    } else {
                        throw;
                    }
                } finally {

                    // don't update remote services that haven't changed
                    if(dirtyServiceEntity) {
                        service = UpdateService(service);
                    }
                }
                stopwatch.Stop();
                _log.InfoFormat("Service '{0}' ({1}) started in {2}ms", service.Description, service.SID, stopwatch.ElapsedMilliseconds);
                return service;
            } finally {

                // restore the request id
                dreamContext.SetState(DreamHeaders.DREAM_REQUEST_ID, requestId);
            }
        }
Esempio n. 26
0
 private void AddOrReplace(XDoc doc, string key, string value) {
     if(value != null) {
         XDoc item = doc[key];
         if(item.IsEmpty) {
             doc.Elem(key, value);
         } else {
             item.ReplaceValue(value);
         }
     }
 }
Esempio n. 27
0
        //--- Class Methods ---
        private static int Main(string[] args)
        {
            bool     useTty = true;
            TimeSpan time;

            // process command line arguments
            XDoc config = new XDoc("config");

            for (int i = 0; i < args.Length; i += 2)
            {
                string key   = args[i].ToLowerInvariant();
                string value = ((i + 1) < args.Length) ? args[i + 1] : string.Empty;
                switch (key)
                {
                case "help":
                    PrintUsage();
                    return(0);

                case "notty":
                    --i;
                    useTty = false;
                    break;

                case "capture-stack-trace":
                    --i;
                    DebugUtil.CaptureStackTrace = true;
                    break;

                case "nolog":
                    --i;

                    // NOTE (steveb): this option used to disable logging, but was removed in favor of using the automatic re-reading of app.config by log4net

                    break;

                case "settings":
                case "config":
                    if (!File.Exists(value))
                    {
                        WriteError(key, "config file not found");
                        return(1);
                    }
                    config = XDocFactory.LoadFrom(value, MimeType.XML);
                    break;

                case "script":
                    config.Start("script").Attr("src", value).End();
                    break;

                case "ip":
                case "host":
                    config.Elem("host", value);
                    break;

                case "http-port":
                case "path-prefix":
                case "server-path":
                case "server-name":
                case "storage-dir":
                case "connect-limit":
                case "apikey":
                case "guid":
                    config.Elem(key, value);
                    break;

                case "public-uri":
                case "root-uri":
                    config.Elem("uri.public", value);
                    break;

                case "service-dir":
                    config.Elem("storage-dir", value);
                    break;

                case "collect-interval":
                    int interval;
                    if (!int.TryParse(value, out interval))
                    {
                        WriteError(key, "invalid collection interval (must be an integer representing seconds)");
                        return(1);
                    }
                    if (interval > 0)
                    {
                        DebugUtil.SetCollectionInterval(TimeSpan.FromSeconds(interval));
                    }
                    break;

                case "auth":
                    config.Elem("authentication-shemes", value);
                    break;

                default:
                    WriteError(key, "unknown setting");
                    return(1);
                }
            }
            try {
                // initialize environment
                if (config["apikey"].IsEmpty)
                {
                    string apikey = StringUtil.CreateAlphaNumericKey(32);
                    config.Elem("apikey", apikey);
                    Console.WriteLine("Dream Host APIKEY: {0}", apikey);
                }
                Console.WriteLine("-------------------- initializing");
                time = DebugUtil.Stopwatch(() => {
                    _host = new DreamHost(config);
                });
                Console.WriteLine("-------------------- initialized {0} secs", time.TotalSeconds);

                // execute scripts
                time = DebugUtil.Stopwatch(() => {
                    _host.RunScripts(config, null);
                });
                Console.WriteLine("-------------------- ready {0} secs", time.TotalSeconds);

                // for UNIX systems, let's also listen to SIGTERM
                if (SysUtil.IsUnix)
                {
                    new Thread(SigTermHandler)
                    {
                        IsBackground = true
                    }.Start();
                }

                // check if we can use the console
                if (useTty)
                {
                    int debuglevel = 0;

                    // wait for user input then exit
                    while (_host.IsRunning)
                    {
                        Thread.Sleep(250);
                        #region Interactive Key Handler
                        if (Console.KeyAvailable)
                        {
                            ConsoleKeyInfo key = Console.ReadKey(true);
                            switch (key.Key)
                            {
                            case ConsoleKey.Q:
                            case ConsoleKey.Escape:
                            case ConsoleKey.Spacebar:
                                Console.WriteLine("Shutting down");
                                return(0);

                            case ConsoleKey.G:
                                Console.WriteLine("Full garbage collection pass");
                                System.GC.Collect();
                                break;

                            case ConsoleKey.C:
                                Console.Clear();
                                break;

                            case ConsoleKey.D:
                                switch (++debuglevel)
                                {
                                default:
                                    debuglevel = 0;
                                    Threading.RendezVousEvent.CaptureTaskState = false;
                                    DebugUtil.CaptureStackTrace = false;
                                    Console.WriteLine("Debug capture: none");
                                    break;

                                case 1:
                                    Threading.RendezVousEvent.CaptureTaskState = true;
                                    DebugUtil.CaptureStackTrace = false;
                                    Console.WriteLine("Debug capture: task-state only");
                                    break;

                                case 2:
                                    Threading.RendezVousEvent.CaptureTaskState = true;
                                    DebugUtil.CaptureStackTrace = true;
                                    Console.WriteLine("Debug capture: task-state and stack-trace");
                                    break;
                                }
                                break;

                            case ConsoleKey.I: {
                                Console.WriteLine("--- System Information ---");

                                // show memory
                                Console.WriteLine("Allocated memory: {0}", GC.GetTotalMemory(false));

                                // show threads
                                int workerThreads;
                                int completionThreads;
                                int dispatcherThreads;
                                int backgroundThreads;
                                AsyncUtil.GetAvailableThreads(out workerThreads, out completionThreads, out dispatcherThreads, out backgroundThreads);
                                int maxWorkerThreads;
                                int maxCompletionThreads;
                                int maxDispatcherThreads;
                                int maxBackgroundThreads;
                                AsyncUtil.GetMaxThreads(out maxWorkerThreads, out maxCompletionThreads, out maxDispatcherThreads, out maxBackgroundThreads);
                                Console.WriteLine("Thread-pool worker threads available: {0} (max: {1})", workerThreads, maxWorkerThreads);
                                Console.WriteLine("Thread-pool completion threads available: {0} (max: {1})", completionThreads, maxCompletionThreads);
                                Console.WriteLine("Dispatcher threads available: {0} (max: {1})", dispatcherThreads, maxDispatcherThreads);
                                Console.WriteLine("Thread-pool background worker threads available: {0} (max: {1})", backgroundThreads, maxBackgroundThreads);

                                // show pending/waiting timers
                                var taskTimerStats = Tasking.TaskTimerFactory.GetStatistics();
                                Console.WriteLine("Pending timer objects: {0}", taskTimerStats.PendingTimers);
                                Console.WriteLine("Queued timer objects: {0}", taskTimerStats.QueuedTimers);
                                Console.WriteLine("Timer retries: {0}", taskTimerStats.Retries);

                                // show activities
                                var activities = _host.ActivityMessages;
                                Console.WriteLine("Host activities: {0}", activities.Length);
                                foreach (var activity in activities)
                                {
                                    Console.WriteLine("* {0}: {1}", activity.Created.ToString(XDoc.RFC_DATETIME_FORMAT), activity.Description);
                                }

                                // show pending tasks
                                Console.WriteLine("Pending rendez-vous events: {0}", Threading.RendezVousEvent.PendingCounter);
                                Console.WriteLine("Pending results: {0}", AResult.PendingCounter);
                                lock (Threading.RendezVousEvent.Pending) {
                                    int count = 0;
                                    foreach (var entry in Threading.RendezVousEvent.Pending.Values)
                                    {
                                        ++count;
                                        if (entry.Key != null)
                                        {
                                            var context = entry.Key.GetState <DreamContext>();
                                            if (context != null)
                                            {
                                                Console.WriteLine("--- DreamContext for pending rendez-vous event #{0} ---", count);
                                                Console.WriteLine(context.Uri.ToString(false));
                                            }
                                        }
                                        Console.WriteLine();
                                        if (entry.Value != null)
                                        {
                                            Console.WriteLine("--- Stack trace for pending rendez-vous event #{0} ---", count);
                                            Console.WriteLine(entry.Value.ToString());
                                        }
                                    }
                                }
                                Console.WriteLine("--------------------------");
                            }
                            break;

                            case ConsoleKey.H:
                                Console.WriteLine("Help:");
                                Console.WriteLine("   Q     - quit application");
                                Console.WriteLine("   ESC   - quit application");
                                Console.WriteLine("   SPACE - quit application");
                                Console.WriteLine("   G     - full garbage collection");
                                Console.WriteLine("   C     - clear screen");
                                Console.WriteLine("   D     - set debug capture level");
                                Console.WriteLine("   I     - show system information (memory, threads, pending tasks)");
                                Console.WriteLine("   H     - this help text");
                                break;
                            }
                        }
                        #endregion
                    }
                }
                else
                {
                    _host.WaitUntilShutdown();
                }
            } finally {
                Console.WriteLine("-------------------- shutting down");
                TaskTimerFactory.ShutdownAll();
                if (_host != null)
                {
                    _host.Dispose();
                }
            }
            return(0);
        }
        public static XDoc WebToggle(
            [DekiScriptParam("content to toggle")] XDoc content,
            [DekiScriptParam("title to display for toggle (default: \"Show\")", true)] string title,
            [DekiScriptParam("heading level for title (default: 3)", true)] int?heading,
            [DekiScriptParam("content toggle speed (one of \"slow\", \"normal\", \"fast\" or milliseconds number; default: instantaneous)", true)] string speed,
            [DekiScriptParam("hide content initially (default: true)", true)] bool?hidden
            )
        {
            if (!content["body[not(@target)]"].IsEmpty)
            {
                string id = StringUtil.CreateAlphaNumericKey(8);

                // clone content so we don't modify the original
                content = content.Clone();
                XDoc body = content["body[not(@target)]"];

                // add <style> element
                XDoc head = content["head"];
                if (head.IsEmpty)
                {
                    content.Elem("head");
                    head = content["head"];
                }
                head.Elem("style",
                          @"h1.web-expand,
h2.web-expand,
h3.web-expand,
h4.web-expand,
h5.web-expand,
h6.web-expand {
	cursor: pointer;
}
.web-expand span.web-expander { 
    padding-right: 20px;
    background: transparent url('/skins/common/images/nav-parent-open.gif') no-repeat center right;
} 
.web-expanded span.web-expander { 
    background: transparent url('/skins/common/images/nav-parent-docked.gif') no-repeat center right; 
}");

                // set speed
                if (string.IsNullOrEmpty(speed))
                {
                    speed = string.Empty;
                }
                else
                {
                    int millisec;
                    if (int.TryParse(speed, out millisec))
                    {
                        speed = millisec.ToString();
                    }
                    else
                    {
                        speed = "'" + speed + "'";
                    }
                }

                // create toggelable content
                bool hide = hidden ?? true;
                content
                .Start("body")
                .Start("h" + Math.Max(1, Math.Min(heading ?? 3, 6)))
                .Attr("class", "web-expand" + (hide ? string.Empty : " web-expanded"))
                .Attr("onclick", "$(this).toggleClass('web-expanded').next('#" + id + "').toggle(" + speed + ")")
                .Start("span")
                .Attr("class", "web-expander")
                .Value(title ?? "Show")
                .End()
                .End()
                .Start("div")
                .Attr("id", id)
                .Attr("style", hide ? "display: none;" : string.Empty)
                .AddNodes(body)
                .End()
                .End();
                body.Remove();
            }
            return(content);
        }
Esempio n. 29
0
        public Yield GetNavigationSiblings(DreamContext context, DreamMessage request, Result<DreamMessage> response) {
            CheckResponseCache(context, false);

            PageBE page = PageBL_GetPageFromUrl(context, false);
            if (page.Title.IsTalk) {
                page = PageBL.GetPageByTitle(page.Title.AsFront());
            }

            // build response
            IList<NavBE> list = NavBL.QueryNavSiblingsData(page, context.Culture);
            if(ShowDebug(context)) {
                response.Return(DreamMessage.Ok(NavBL.ConvertNavPageListToDoc(list)));
            } else {
                XDoc doc = NavBL.ComputeNavigationDocument(list, page, (uint)page.ID, 0, true, context.GetParam("width", int.MaxValue));
                if(ShowXml(context)) {
                    response.Return(DreamMessage.Ok(doc));
                } else {
                    XDoc result = new XDoc("tree");
                    result.Start("siblings");

                    // add name of sibling nodes
                    System.Text.StringBuilder nodes = new System.Text.StringBuilder();
                    ulong homepageId = DekiContext.Current.Instance.HomePageId;
                    foreach(NavBE sibling in list) {
                        if((sibling.ParentId == page.ParentID) && (sibling.Id != homepageId)) {
                            if(nodes.Length != 0) {
                                nodes.Append(",");
                            }
                            nodes.AppendFormat("n{0}", sibling.Id);
                        }
                    }
                    result.Elem("nodes", nodes.ToString());

                    // add sibling nodes
                    result.Start("html");
                    result.Elem("pre", doc["siblings-pre"].Contents);
                    result.Elem("post", doc["siblings-post"].Contents);
                    result.End();
                    result.End();
                    response.Return(DreamMessage.Ok(result));
                }
            }
            yield break;
        }
        private void MovePermissions(ACConverterPageInfo pageInfo)
        {
            RemotePermission[] pagePermissions = _confluenceService.GetPagePermissions(pageInfo.ConfluencePage.id);

            //Change permissions list according to parent page permissoins
            List <RemotePermission> newPermissions = new List <RemotePermission>();

            foreach (RemotePermission permission in pageInfo.ConfluenceUsersWithViewPermissions.Values)
            {
                newPermissions.Add(permission);
            }
            foreach (RemotePermission permission in pagePermissions)
            {
                if (permission.lockType == ConfluenceEditPermissionName)
                {
                    if ((pageInfo.ConfluenceUsersWithViewPermissions.Count == 0) || (pageInfo.ConfluenceUsersWithViewPermissions.ContainsKey(permission.lockedBy.ToLower())))
                    {
                        newPermissions.Add(permission);
                    }
                }
            }

            pagePermissions = newPermissions.ToArray();

            if (pagePermissions.Length == 0)
            {
                return;
            }

            string dekiRestriction;

            //Possible two entry of one user or group in pagePermissions.
            //As View permission and as Edit permission for this group/user.
            //To prevent repeated addition to Deki in this dictionary stored true
            //if permission to this user/group added to Deki.
            Dictionary <string, bool> permissionAddedToDeki = new Dictionary <string, bool>();

            Dictionary <string, bool> userHaveWritePermission = new Dictionary <string, bool>();

            if (_compatibleConvertUserPermissions)
            {
                bool onlyWriteRestrictions = true;
                foreach (RemotePermission permission in pagePermissions)
                {
                    if (permission.lockType == ConfluenceViewPermissionName)
                    {
                        onlyWriteRestrictions = false;
                        break;
                    }
                }
                if (onlyWriteRestrictions)
                {
                    //If there no view restrictions on this Confluence page set Semi-Public restrictions to Deki users
                    dekiRestriction = "Semi-Public";
                }
                else
                {
                    //If there is view restrictions on this Confluence page to allow users/groups with View and Edit
                    //restrictions view this page set Private restriction in Deki.
                    //Users without Edit permission but with View permission in Confluence can edit this page in Deki.
                    dekiRestriction = "Private";
                }
            }
            else
            {
                dekiRestriction = "Private";

                foreach (RemotePermission permission in pagePermissions)
                {
                    if (permission.lockType == ConfluenceEditPermissionName)
                    {
                        userHaveWritePermission[permission.lockedBy.ToLower()] = true;
                    }
                    else
                    {
                        if (!userHaveWritePermission.ContainsKey(permission.lockedBy.ToLower()))
                        {
                            userHaveWritePermission[permission.lockedBy.ToLower()] = false;
                        }
                    }
                }
            }

            XDoc securityDoc = new XDoc("security")
                               .Start("permissions.page")
                               .Elem("restriction", dekiRestriction)
                               .End()
                               .Start("grants");

            foreach (RemotePermission permission in pagePermissions)
            {
                if (permissionAddedToDeki.ContainsKey(permission.lockedBy.ToLower()))
                {
                    continue;
                }

                securityDoc
                .Start("grant")
                .Start("permissions");
                if (_compatibleConvertUserPermissions)
                {
                    securityDoc.Elem("role", "Contributor");
                }
                else
                {
                    bool haveWritePermission = false;
                    userHaveWritePermission.TryGetValue(permission.lockedBy.ToLower(), out haveWritePermission);
                    if (haveWritePermission)
                    {
                        securityDoc.Elem("role", "Contributor");
                    }
                    else
                    {
                        securityDoc.Elem("role", "Viewer");
                    }
                }
                securityDoc.End();

                //Detect if this is group or user permission
                ACConverterUserInfo dekiUser;
                if (_convertedUsers.TryGetValue(permission.lockedBy.ToLower(), out dekiUser))
                {
                    securityDoc.Start("user").Attr("id", dekiUser.DekiUserId).End();
                }
                else
                {
                    ACConverterGroupInfo dekiGroup = null;
                    if (_convertedGroups.TryGetValue(permission.lockedBy.ToLower(), out dekiGroup))
                    {
                        securityDoc.Start("group").Attr("id", dekiGroup.DekiGroupId).End();
                    }
                    else
                    {
                        WriteLineToConsole("Page " + pageInfo.ConfluencePage.title + " locked by " + permission.lockedBy +
                                           " that is not a user and not a group. Restriction ignored.");
                    }
                }
                securityDoc.End();

                permissionAddedToDeki[permission.lockedBy.ToLower()] = true;
            }

            securityDoc.End();

            DreamMessage res = _dekiPlug.At("pages", pageInfo.DekiPageId.ToString(), "security").PutAsync(securityDoc).Wait();

            if (res.Status != DreamStatus.Ok)
            {
                WriteLineToLog("Error converting permissions");
                WriteErrorResponse(res);
                WriteErrorRequest(securityDoc);
            }
        }
Esempio n. 31
0
        //--- Methods ---
        private void AddFunction(XDoc result, string ns, XDoc function)
        {
            result.Start("blockquote");
            List <Tuplet <string, bool, string, string> > args = new List <Tuplet <string, bool, string, string> >();
            StringBuilder signature = new StringBuilder();

            signature.Append(((ns != null) ? ns + "." : string.Empty) + function["name"].AsText);
            if (string.IsNullOrEmpty(function["@usage"].AsText))
            {
                signature.Append("(");

                // enumerate arguments
                int count = 1;
                foreach (XDoc arg in function["param"])
                {
                    // add argument to signature
                    if (count > 1)
                    {
                        signature.Append(", ");
                    }
                    string name = arg["@name"].AsText ?? arg["name"].AsText ?? ("arg" + count.ToString());
                    signature.Append(name);
                    string type = arg["@type"].AsText ?? arg["type"].AsText;
                    if (type != null)
                    {
                        signature.Append(" : ");
                        signature.Append(type);
                    }
                    ++count;

                    // add argument to explanation
                    if (!arg["hint"].IsEmpty || !string.IsNullOrEmpty(arg.AsText))
                    {
                        args.Add(new Tuplet <string, bool, string, string>(name, StringUtil.EqualsInvariant(arg["@optional"].AsText, "true") || !arg["@default"].IsEmpty || !arg["hint[@optional='true']"].IsEmpty, arg["hint"].AsText ?? arg.AsText, arg["@default"].AsText));
                    }
                }
                signature.Append(")");
            }
            signature.Append(" : ").Append(function["return/@type"].AsText ?? "any");
            result.Elem("h3", signature.ToString());
            if (function["description"].AsText != null)
            {
                result.Elem("p", function["description"].AsText);
            }

            // add argument explanation
            if (args.Count > 0)
            {
                result.Start("ul");
                foreach (Tuplet <string, bool, string, string> arg in args)
                {
                    result.Start("li");
                    result.Elem("strong", arg.Item1);
                    if (arg.Item2)
                    {
                        result.Value(" (optional)");
                    }
                    result.Value(": " + arg.Item3);
                    if (arg.Item4 != null)
                    {
                        result.Value(" (default: " + arg.Item4 + ")");
                    }
                    result.End();
                }
                result.End();
            }
            result.Elem("br");
            result.End();
        }
Esempio n. 32
0
        /// <summary>
        /// Create a new host with provided configuration and an Inversion of Control container.
        /// </summary>
        /// <remarks>
        /// The IoC container is also injected into default activator, so that <see cref="IDreamService"/> instances
        /// can be resolved from the container. The host configuration is provided to the container as a typed parameter.
        /// </remarks>
        /// <param name="config">Host configuration.</param>
        /// <param name="container">IoC Container.</param>
        public DreamHost(XDoc config, IContainer container)
        {
            if (config == null)
            {
                throw new ArgumentNullException("config");
            }

            // read host settings
            string appDirectory = Path.GetDirectoryName(System.Reflection.Assembly.GetExecutingAssembly().GetModules()[0].FullyQualifiedName);
            int    limit        = config["connect-limit"].AsInt ?? 0;
            int    httpPort     = config["http-port"].AsInt ?? DEFAULT_PORT;
            AuthenticationSchemes authenticationScheme = AuthenticationSchemes.Anonymous;
            string authShemes = config["authentication-shemes"].AsText;

            if (!String.IsNullOrEmpty(authShemes))
            {
                try {
                    authenticationScheme = (AuthenticationSchemes)Enum.Parse(typeof(AuthenticationSchemes), authShemes, true);
                } catch (Exception e) {
                    _log.Warn(String.Format("invalid authetication scheme specified :{0}", authShemes), e);
                }
            }

            // get the authtoken for whitelisting dream.in.* query args
            _dreamInParamAuthtoken = config["dream.in.authtoken"].AsText;
            if (!string.IsNullOrEmpty(_dreamInParamAuthtoken))
            {
                _log.Debug("Host is configured in dream.in param authorizing mode");
            }

            // read ip-addresses
            var addresses = new List <string>();

            foreach (XDoc ip in config["host|ip"])
            {
                addresses.Add(ip.AsText);
            }
            if (addresses.Count == 0)
            {
                // if no addresses were supplied listen to all
                addresses.Add("*:" + httpPort);
            }

            // use default servername
            XUri publicUri = config["uri.public"].AsUri;

            if (publicUri == null)
            {
                // backwards compatibility
                publicUri = config["server-name"].AsUri;
                if (publicUri == null)
                {
                    foreach (IPAddress addr in Dns.GetHostAddresses(Dns.GetHostName()))
                    {
                        if (addr.AddressFamily == AddressFamily.InterNetwork)
                        {
                            XUri.TryParse("http://" + addr, out publicUri);
                        }
                    }
                    if (publicUri == null)
                    {
                        // failed to get an address out of dns, fall back to localhost
                        XUri.TryParse("http://localhost", out publicUri);
                    }
                }
                publicUri = publicUri.AtPath(config["server-path"].AsText ?? config["path-prefix"].AsText ?? string.Empty);
            }

            // create environment and initialize it
            _env = new DreamHostService(container);
            try {
                // initialize environment
                string apikey        = config["apikey"].AsText ?? StringUtil.CreateAlphaNumericKey(32);
                XDoc   serviceConfig = new XDoc("config");
                var    storageType   = config["storage/@type"].AsText ?? "local";
                if ("s3".EqualsInvariant(storageType))
                {
                    serviceConfig.Add(config["storage"]);
                }
                else
                {
                    serviceConfig.Elem("storage-dir", config["storage-dir"].AsText ?? config["service-dir"].AsText ?? appDirectory);
                }
                serviceConfig.Elem("apikey", apikey);
                serviceConfig.Elem("uri.public", publicUri);
                serviceConfig.Elem("connect-limit", limit);
                serviceConfig.Elem("guid", config["guid"].AsText);
                serviceConfig.AddAll(config["components"]);
                var memorize = config["memorize-aliases"];
                if (!memorize.IsEmpty)
                {
                    serviceConfig.Elem("memorize-aliases", memorize.AsBool);
                }
                _env.Initialize(serviceConfig);

                // initialize host plug
                _host = _env.Self.With("apikey", apikey);

                // load assemblies in 'services' folder
                string servicesFolder = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, "services");
                if (Directory.Exists(servicesFolder))
                {
                    // Note (arnec): Deprecated, but the suggested alternative really doesn't apply since we don't want to
                    // load services into a separate appdomain.
#pragma warning disable 618,612
                    AppDomain.CurrentDomain.AppendPrivatePath("services");
#pragma warning restore 618,612
                    foreach (string file in Directory.GetFiles(servicesFolder, "*.dll"))
                    {
                        // register assembly blueprints
                        DreamMessage response = _host.At("load").With("name", Path.GetFileNameWithoutExtension(file)).Post(new Result <DreamMessage>(TimeSpan.MaxValue)).Wait();
                        if (!response.IsSuccessful)
                        {
                            _log.WarnFormat("DreamHost: ERROR: assembly '{0}' failed to load", file);
                        }
                    }
                }

                // add acccess-points
                AddListener(new XUri(String.Format("http://{0}:{1}/", "localhost", httpPort)), authenticationScheme);

                // check if user prescribed a set of IP addresses to use
                if (addresses != null)
                {
                    // listen to custom addresses (don't use the supplied port info, we expect that to be part of the address)
                    foreach (string address in addresses)
                    {
                        if (!StringUtil.EqualsInvariantIgnoreCase(address, "localhost"))
                        {
                            AddListener(new XUri(String.Format("http://{0}/", address)), authenticationScheme);
                        }
                    }
                }
                else
                {
                    // add listeners for all known IP addresses
                    foreach (IPAddress address in Dns.GetHostAddresses(Dns.GetHostName()))
                    {
                        XUri uri = MakeUri(address, httpPort);
                        if (uri != null)
                        {
                            AddListener(uri, authenticationScheme);
                            try {
                                foreach (string alias in Dns.GetHostEntry(address).Aliases)
                                {
                                    AddListener(new XUri(String.Format("http://{0}:{1}/", alias, httpPort)), authenticationScheme);
                                }
                            } catch { }
                        }
                    }
                }
            } catch (Exception e) {
                if ((e is HttpListenerException) && e.Message.EqualsInvariant("Access is denied"))
                {
                    _log.ErrorExceptionMethodCall(e, "ctor", "insufficient privileges to create HttpListener, make sure the application runs with Administrator rights");
                }
                else
                {
                    _log.ErrorExceptionMethodCall(e, "ctor");
                }
                try {
                    _env.Deinitialize();
                } catch { }
                throw;
            }
        }
Esempio n. 33
0
        //--- Class Methods ---
        private static int Main(string[] args)
        {
            bool useTty = true;
            TimeSpan time;

            // process command line arguments
            XDoc config = new XDoc("config");
            for(int i = 0; i < args.Length; i += 2) {
                string key = args[i].ToLowerInvariant();
                string value = ((i + 1) < args.Length) ? args[i + 1] : string.Empty;
                switch(key) {
                case "help":
                    PrintUsage();
                    return 0;
                case "notty":
                    --i;
                    useTty = false;
                    break;
                case "capture-stack-trace":
                    --i;
                    DebugUtil.CaptureStackTrace = true;
                    break;
                case "nolog":
                    --i;

                    // NOTE (steveb): this option used to disable logging, but was removed in favor of using the automatic re-reading of app.config by log4net

                    break;
                case "settings":
                case "config":
                    if(!File.Exists(value)) {
                        WriteError(key, "config file not found");
                        return 1;
                    }
                    config = XDocFactory.LoadFrom(value, MimeType.XML);
                    break;
                case "script":
                    config.Start("script").Attr("src", value).End();
                    break;
                case "ip":
                case "host":
                    config.Elem("host", value);
                    break;
                case "http-port":
                case "path-prefix":
                case "server-path":
                case "server-name":
                case "storage-dir":
                case "connect-limit":
                case "apikey":
                case "guid":
                    config.Elem(key, value);
                    break;
                case "public-uri":
                case "root-uri":
                    config.Elem("uri.public", value);
                    break;
                case "service-dir":
                    config.Elem("storage-dir", value);
                    break;
                case "collect-interval":
                    int interval;
                    if(!int.TryParse(value, out interval)) {
                        WriteError(key, "invalid collection interval (must be an integer representing seconds)");
                        return 1;
                    }
                    if(interval > 0) {
                        DebugUtil.SetCollectionInterval(TimeSpan.FromSeconds(interval));
                    }
                    break;
                case "auth":
                    config.Elem("authentication-shemes", value);
                    break;
                default:
                    WriteError(key, "unknown setting");
                    return 1;
                }
            }
            try {

                // initialize environment
                if(config["apikey"].IsEmpty) {
                    string apikey = StringUtil.CreateAlphaNumericKey(32);
                    config.Elem("apikey", apikey);
                    Console.WriteLine("Dream Host APIKEY: {0}", apikey);
                }
                Console.WriteLine("-------------------- initializing");
                time = DebugUtil.Stopwatch(() => {
                    _host = new DreamHost(config);
                });
                Console.WriteLine("-------------------- initialized {0} secs", time.TotalSeconds);

                // execute scripts
                time = DebugUtil.Stopwatch(() => {
                    _host.RunScripts(config, null);
                });
                Console.WriteLine("-------------------- ready {0} secs", time.TotalSeconds);

                // for UNIX systems, let's also listen to SIGTERM
                if(SysUtil.IsUnix) {
                    new Thread(SigTermHandler) { IsBackground = true }.Start();
                }

                // check if we can use the console
                if(useTty) {
                    int debuglevel = 0;

                    // wait for user input then exit
                    while(_host.IsRunning) {
                        Thread.Sleep(250);
                        #region Interactive Key Handler
                        if(Console.KeyAvailable) {
                            ConsoleKeyInfo key = Console.ReadKey(true);
                            switch(key.Key) {
                            case ConsoleKey.Q:
                            case ConsoleKey.Escape:
                            case ConsoleKey.Spacebar:
                                Console.WriteLine("Shutting down");
                                return 0;
                            case ConsoleKey.G:
                                Console.WriteLine("Full garbage collection pass");
                                System.GC.Collect();
                                break;
                            case ConsoleKey.C:
                                Console.Clear();
                                break;
                            case ConsoleKey.D:
                                switch(++debuglevel) {
                                default:
                                    debuglevel = 0;
                                    Threading.RendezVousEvent.CaptureTaskState = false;
                                    DebugUtil.CaptureStackTrace = false;
                                    Console.WriteLine("Debug capture: none");
                                    break;
                                case 1:
                                    Threading.RendezVousEvent.CaptureTaskState = true;
                                    DebugUtil.CaptureStackTrace = false;
                                    Console.WriteLine("Debug capture: task-state only");
                                    break;
                                case 2:
                                    Threading.RendezVousEvent.CaptureTaskState = true;
                                    DebugUtil.CaptureStackTrace = true;
                                    Console.WriteLine("Debug capture: task-state and stack-trace");
                                    break;
                                }
                                break;
                            case ConsoleKey.I: {
                                    Console.WriteLine("--- System Information ---");

                                    // show memory
                                    Console.WriteLine("Allocated memory: {0}", GC.GetTotalMemory(false));

                                    // show threads
                                    int workerThreads;
                                    int completionThreads;
                                    int dispatcherThreads;
                                    int backgroundThreads;
                                    AsyncUtil.GetAvailableThreads(out workerThreads, out completionThreads, out dispatcherThreads, out backgroundThreads);
                                    int maxWorkerThreads;
                                    int maxCompletionThreads;
                                    int maxDispatcherThreads;
                                    int maxBackgroundThreads;
                                    AsyncUtil.GetMaxThreads(out maxWorkerThreads, out maxCompletionThreads, out maxDispatcherThreads, out maxBackgroundThreads);
                                    Console.WriteLine("Thread-pool worker threads available: {0} (max: {1})", workerThreads, maxWorkerThreads);
                                    Console.WriteLine("Thread-pool completion threads available: {0} (max: {1})", completionThreads, maxCompletionThreads);
                                    Console.WriteLine("Dispatcher threads available: {0} (max: {1})", dispatcherThreads, maxDispatcherThreads);
                                    Console.WriteLine("Thread-pool background worker threads available: {0} (max: {1})", backgroundThreads, maxBackgroundThreads);

                                    // show pending/waiting timers
                                    var taskTimerStats = Tasking.TaskTimerFactory.GetStatistics();
                                    Console.WriteLine("Pending timer objects: {0}", taskTimerStats.PendingTimers);
                                    Console.WriteLine("Queued timer objects: {0}", taskTimerStats.QueuedTimers);
                                    Console.WriteLine("Timer retries: {0}", taskTimerStats.Retries);

                                    // show activities
                                    var activities = _host.ActivityMessages;
                                    Console.WriteLine("Host activities: {0}", activities.Length);
                                    foreach(var activity in activities) {
                                        Console.WriteLine("* {0}: {1}", activity.Created.ToString(XDoc.RFC_DATETIME_FORMAT), activity.Description);
                                    }

                                    // show pending tasks
                                    Console.WriteLine("Pending rendez-vous events: {0}", Threading.RendezVousEvent.PendingCounter);
                                    Console.WriteLine("Pending results: {0}", AResult.PendingCounter);
                                    lock(Threading.RendezVousEvent.Pending) {
                                        int count = 0;
                                        foreach(var entry in Threading.RendezVousEvent.Pending.Values) {
                                            ++count;
                                            if(entry.Key != null) {
                                                var context = entry.Key.GetState<DreamContext>();
                                                if(context != null) {
                                                    Console.WriteLine("--- DreamContext for pending rendez-vous event #{0} ---", count);
                                                    Console.WriteLine(context.Uri.ToString(false));
                                                }
                                            }
                                            Console.WriteLine();
                                            if(entry.Value != null) {
                                                Console.WriteLine("--- Stack trace for pending rendez-vous event #{0} ---", count);
                                                Console.WriteLine(entry.Value.ToString());
                                            }
                                        }
                                    }
                                    Console.WriteLine("--------------------------");
                                }
                                break;
                            case ConsoleKey.H:
                                Console.WriteLine("Help:");
                                Console.WriteLine("   Q     - quit application");
                                Console.WriteLine("   ESC   - quit application");
                                Console.WriteLine("   SPACE - quit application");
                                Console.WriteLine("   G     - full garbage collection");
                                Console.WriteLine("   C     - clear screen");
                                Console.WriteLine("   D     - set debug capture level");
                                Console.WriteLine("   I     - show system information (memory, threads, pending tasks)");
                                Console.WriteLine("   H     - this help text");
                                break;
                            }
                        }
                        #endregion
                    }
                } else {
                    _host.WaitUntilShutdown();
                }
            } finally {
                Console.WriteLine("-------------------- shutting down");
                TaskTimerFactory.ShutdownAll();
                if(_host != null) {
                    _host.Dispose();
                }
            }
            return 0;
        }
Esempio n. 34
0
        public static XDoc ComputeNavigationDocument(IList <NavBE> list, PageBE page, uint splitSibling, uint splitChildren, bool hidden, int max_width)
        {
            XDoc          result          = new XDoc("tree");
            List <string> css             = new List <string>();
            List <string> fetchedChildren = new List <string>();
            List <NavBE>  childrenNodes   = new List <NavBE>();
            ulong         homepageId      = DekiContext.Current.Instance.HomePageId;
            NavDocStage   stage           = NavDocStage.None;

            if (splitSibling > 0)
            {
                stage = NavDocStage.SiblingPre;
                result.Start("siblings-pre");
            }
            else if (splitChildren > 0)
            {
                stage = NavDocStage.ChildrenPre;
                result.Start("siblings-pre").End();
                result.Start("children-pre");
            }
            int splitSiblingIndex  = 0;
            int splitChildrenIndex = 0;

            // fix page_parent_id: it's stored as zero for home and children of home
            ulong page_parent_id = page.ParentID;

            if ((page_parent_id == 0) && (page.ID != homepageId))
            {
                page_parent_id = homepageId;
            }
            int page_index = 0;

            // iterate over result set
            int siblingIndex = 0;
            int childIndex   = 0;

            foreach (NavBE node in list)
            {
                // retrieve page values
                uint  node_id        = node.Id;
                ulong node_parent_id = node.ParentId;
                bool  virtual_node   = (node_id >= NEW_PAGE_ID);

                // fix parent_id: it's stored as zero for home and children of home
                if ((node_parent_id == 0) && (node_id != homepageId))
                {
                    node_parent_id = homepageId;
                }

                // set node index (if possible)
                if (node_id == page.ID)
                {
                    page_index = siblingIndex;
                }

                // check if we need to split the output
                if (node_id == splitSibling)
                {
                    splitSiblingIndex = siblingIndex;
                    stage             = NavDocStage.ChildrenPre;
                    result.End().Start("children-pre");
                    if (splitChildren == 0)
                    {
                        stage = NavDocStage.ChildrenPost;
                        result.End().Start("children-post");
                    }
                    continue;
                }
                if (node_id == splitChildren)
                {
                    splitChildrenIndex = childIndex;
                    stage = NavDocStage.ChildrenPost;
                    result.End().Start("children-post");
                    continue;
                }
                if (((stage == NavDocStage.ChildrenPre) || (stage == NavDocStage.ChildrenPost)) && (splitSibling > 0) && (node_parent_id != splitSibling))
                {
                    if (stage == NavDocStage.ChildrenPre)
                    {
                        result.End().Start("children-post");
                    }
                    stage = NavDocStage.SiblingPost;
                    result.End().Start("siblings-post");
                }

                // check if this node is part of the result set (only include ancestors, siblings, and children of selected node)
                bool  ancestor  = false;
                Title nodeTitle = Title.FromDbPath((NS)node.NameSpace, node.Title, node.DisplayName);
                if ((node_id != page.ID /* selected */) && (node_parent_id != page_parent_id /* sibling */) && (node_parent_id != page.ID /* child */))
                {
                    ancestor = (node_id == page_parent_id /* immediate parent */) || (node_id == homepageId) || nodeTitle.IsParentOf(page.Title);
                    if (!ancestor)
                    {
                        continue;
                    }
                }

                // don't include siblings root user pages
                if (((page.Title.IsUser) || (page.Title.IsSpecial) || (page.Title.IsTemplate)) && (page_parent_id == homepageId) && (node_parent_id == homepageId) && (node_id != page.ID))
                {
                    continue;
                }

                // 'div' element
                result.Start("div");

                // 'class' attribute
                css.Clear();
                css.Add("node");
                if (hidden)
                {
                    css.Add("closedNode");
                }

                // 'c' (children) attribute
                fetchedChildren.Clear();
                childrenNodes.Clear();
                uint parentId = (node_id == homepageId) ? 0 : node_id;
                for (int i = 0; i < list.Count; ++i)
                {
                    NavBE child = list[i];
                    if ((child.ParentId == parentId) & (child.Id != homepageId))
                    {
                        Title childTitle = Title.FromDbPath((NS)child.NameSpace, child.Title, child.DisplayName);

                        // skip children if they are siblings of the top User: or Template: page
                        if (((page.Title.IsUser) || (page.Title.IsSpecial) || (page.Title.IsTemplate)) && (node_id == homepageId) && !childTitle.IsParentOf(page.Title))
                        {
                            continue;
                        }
                        childrenNodes.Add(child);
                        fetchedChildren.Add("n" + child.Id);
                    }
                }
                int totalChildrenCount = node.ChildCount ?? fetchedChildren.Count;

                // 'p' (parent) attribute
                string p = null;
                if (node_id != homepageId)
                {
                    p = "n" + node_parent_id;
                }

                // 'cd' (child-data) and 'sd' (sibling-data) attribute
                string cd = null;
                string sd;
                if (node_id == page.ID)
                {
                    // active node
                    if (node_id == homepageId)
                    {
                        css.Add("dockedNode");
                        css.Add("homeNode");
                        css.Add("parentClosed");
                        css.Add("homeSelected");
                    }
                    else
                    {
                        css.Add("childNode");
                        if (!hidden)
                        {
                            css.Add("sibling");
                        }
                        if (totalChildrenCount > 0)
                        {
                            css.Add("parentOpen");
                        }
                    }
                    css.Add("selected");

                    // we have all the child data
                    cd = "1";
                    sd = "1";
                }
                else if (node_parent_id == page_parent_id)
                {
                    // sibling of active node
                    css.Add("childNode");
                    if (!hidden)
                    {
                        css.Add("sibling");
                    }
                    if (totalChildrenCount > 0)
                    {
                        css.Add("parentClosed");
                    }

                    // if no children exist, then we have all the child data
                    cd = ((totalChildrenCount > 0) ? "0" : "1");
                    sd = "1";
                }
                else if (node_parent_id == page.ID)
                {
                    // child of active node
                    css.Add("childNode");
                    if ((node_parent_id == homepageId) && !hidden)
                    {
                        css.Add("sibling");
                    }
                    if ((page.ID != homepageId) && !hidden)
                    {
                        css.Add("selectedChild");
                    }
                    if (totalChildrenCount > 0)
                    {
                        css.Add("parentClosed");
                    }

                    // if no children exist, then we have all the child data
                    cd = ((totalChildrenCount > 0) ? "0" : "1");
                    sd = "1";
                }
                else if (ancestor)
                {
                    // ancestor of active node (parent and above)
                    css.Add("dockedNode");
                    if (node_id == homepageId)
                    {
                        css.Add("homeNode");
                    }
                    if (node_id == page_parent_id)
                    {
                        css.Add("lastDocked");
                    }
                    css.Add("parentClosed");

                    // check if we are the last docked node or have more than one child
                    if ((node_id == page_parent_id) || (totalChildrenCount == 1))
                    {
                        cd = "1";
                    }
                    else
                    {
                        // find the child node that is actually included in the tree
                        foreach (NavBE child in childrenNodes)
                        {
                            Title childTitle = Title.FromDbPath((NS)child.NameSpace, child.Title, child.DisplayName);
                            if (childTitle.IsParentOf(page.Title))
                            {
                                cd = "n" + child.Id;
                                break;
                            }
                        }
                        if (cd == null)
                        {
#if DEBUG
                            throw new Exception("unexpected [expected to find child nodes]");
#else
                            cd = "1";
#endif
                        }
                    }

                    // check if parent of this node has more than one child
                    if ((node_id == homepageId) || (result[string.Format("div[@id='{0}']/@cd", "n" + node_parent_id)].Contents == "1"))
                    {
                        sd = "1";
                    }
                    else
                    {
                        sd = "0";
                    }
                }
                else
                {
                    throw new Exception("unexpected");
                }

                // attributes
                result.Attr("class", string.Join(" ", css.ToArray()));
                result.Attr("id", "n" + node_id.ToString());
                if (fetchedChildren.Count > 0)
                {
                    result.Attr("c", string.Join(",", fetchedChildren.ToArray()));
                }
                if (p != null)
                {
                    result.Attr("p", p);
                }

                // NOTE (steveb): this is used by the JS in the browser to correlate nodes in the pane (it's never used by anything else; hence the different format)
                string safe_path = nodeTitle.AsPrefixedDbPath().Replace("//", "%2f");
                result.Attr("path", (safe_path.Length == 0) ? string.Empty : (safe_path + "/"));

                // root page always has all children if they belong to User:, Template:, or Special: namespace
                if ((cd != "1") && !virtual_node && ((page.Title.IsMain) || (((page.Title.IsTemplate) || (page.Title.IsUser) || (page.Title.IsSpecial)) && (node_id != homepageId))))
                {
                    result.Attr("cd", cd);
                }

                // children of root page always have all siblings if they belong to User:, Template:, or Special: namespace
                if ((sd != "1") && !virtual_node && ((page.Title.IsMain) || (((page.Title.IsTemplate) || (page.Title.IsUser) || (page.Title.IsSpecial)) && (node_parent_id != homepageId))))
                {
                    result.Attr("sd", "0");
                }
                if (virtual_node || ((node_id == homepageId) && (!page.Title.IsMain)))
                {
                    result.Attr("reload", "1");
                }

                // div contents
                result.Start("a");

                // set page title
                string name = nodeTitle.AsUserFriendlyName();
                result.Attr("href", Utils.AsPublicUiUri(nodeTitle));
                result.Attr("title", name);
                result.Elem("span", DekiWikiService.ScreenFont.Truncate(name, max_width));
                result.End();
                result.End();
                if (node_parent_id == page_parent_id)
                {
                    ++siblingIndex;
                }
                else if (node_parent_id == page.ID)
                {
                    ++childIndex;
                }
            }

            // post-process created list
            if ((splitSibling > 0) || (splitChildren > 0))
            {
                if (stage == NavDocStage.SiblingPre)
                {
                    result.End().Start("siblings-post");
                    result.End().Start("children-pre");
                    result.End().Start("children-post");
                }
                else if (stage == NavDocStage.ChildrenPre)
                {
                    result.End().Start("children-post");
                    result.End().Start("siblings-post");
                }
                else if (stage == NavDocStage.ChildrenPost)
                {
                    result.End().Start("siblings-post");
                }
                result.End();

                // truncate siblings and children
                TruncateList(result["siblings-pre/div | siblings-post/div"], ~splitSiblingIndex, hidden);
                TruncateList(result["children-pre/div | children-post/div"], ~splitChildrenIndex, hidden);
            }
            else if (hidden)
            {
                // truncate full list
                TruncateList(result["div"], 0, hidden);
            }
            else
            {
                // truncate children of selected node
                TruncateList(result[string.Format("div[@p='n{0}']", page.ID)], 0, hidden);

                // truncate siblings of selected node
                TruncateList(result[string.Format("div[@p='n{0}']", page_parent_id)], page_index, hidden);
            }
            return(result);
        }
Esempio n. 35
0
 //--- Class Methods ---
 public static void AppendXml(this RecentChangeEntry change, XDoc doc)
 {
     doc.Start("change");
     doc.Elem("rc_id", change.Id);
     if (change.ExtraComments != null)
     {
         foreach (var comment in change.ExtraComments)
         {
             doc.Start("rc_comment")
             .Attr("author", comment.Item1)
             .Attr("fullname", comment.Item2)
             .Value(comment.Item3)
             .End();
         }
     }
     else
     {
         doc.Elem("rc_comment", change.Comment);
     }
     doc.Elem("rc_cur_id", change.CurId);
     doc.Elem("rc_last_oldid", change.LastOldId);
     doc.Elem("rc_this_oldid", change.ThisOldId);
     doc.Elem("rc_namespace", (int)change.Namespace);
     doc.Elem("rc_timestamp", DbUtils.ToString(change.Timestamp));
     doc.Elem("rc_title", change.Title);
     doc.Elem("rc_type", (int)change.Type);
     doc.Elem("rc_moved_to_ns", (int)change.MovedToNs);
     doc.Elem("rc_moved_to_title", change.MovedToTitle);
     if ((change.SortedAuthors != null) && (change.SortedAuthors.Count > 1))
     {
         foreach (var author in change.SortedAuthors)
         {
             doc.Elem("rc_user_name", author.Key);
             doc.Elem("rc_full_name", author.Value);
         }
     }
     else
     {
         doc.Elem("rc_user_name", change.Username);
         doc.Elem("rc_full_name", change.Fullname);
     }
     doc.Elem("rc_page_exists", change.PageExists ? 1 : 0);
     doc.Elem("rc_revision", change.Revision);
     doc.Elem("cmnt_id", change.CmntId);
     doc.Elem("cmnt_number", change.CmntNumber);
     doc.Elem("cmnt_content", change.CmntContent);
     doc.Elem("cmnt_content_mimetype", change.CmntMimetype);
     doc.Elem("cmnt_deleted", change.CmntDeleted ? 1 : 0);
     doc.Elem("old_is_hidden", change.OldIsHidden);
     doc.Elem("edit_count", change.EditCount);
     doc.Elem("rc_prev_revision", change.PreviousRevision);
     doc.Elem("rc_summary", change.Summary);
     doc.End();
 }
Esempio n. 36
0
        public Yield GetNavigationChildrenSiblings(DreamContext context, DreamMessage request, Result <DreamMessage> response)
        {
            CheckResponseCache(context, false);

            PageBE page = PageBL_GetPageFromUrl(context, false);

            if (page.Title.IsTalk)
            {
                page = PageBL.GetPageByTitle(page.Title.AsFront());
            }

            // build response
            uint          exclude = context.GetParam <uint>("exclude", 0);
            IList <NavBE> list    = NavBL.QueryNavSiblingsAndChildrenData(page, context.Culture);

            if (ShowDebug(context))
            {
                response.Return(DreamMessage.Ok(NavBL.ConvertNavPageListToDoc(list)));
            }
            else
            {
                XDoc doc = NavBL.ComputeNavigationDocument(list, page, (uint)page.ID, exclude, true, context.GetParam("width", int.MaxValue));
                if (ShowXml(context))
                {
                    response.Return(DreamMessage.Ok(doc));
                }
                else
                {
                    XDoc result = new XDoc("tree");
                    result.Start("siblings");

                    // add name of sibling nodes
                    System.Text.StringBuilder nodes = new System.Text.StringBuilder();
                    ulong homepageId = DekiContext.Current.Instance.HomePageId;
                    foreach (NavBE sibling in list)
                    {
                        if ((sibling.ParentId == page.ParentID) && (sibling.Id != homepageId))
                        {
                            if (nodes.Length != 0)
                            {
                                nodes.Append(",");
                            }
                            nodes.AppendFormat("n{0}", sibling.Id);
                        }
                    }
                    result.Elem("nodes", nodes.ToString());

                    // add sibling nodes
                    result.Start("html");
                    result.Elem("pre", doc["siblings-pre"].Contents);
                    result.Elem("post", doc["siblings-post"].Contents);
                    result.End();
                    result.End();

                    // add name of children nodes
                    result.Start("children");
                    nodes = new System.Text.StringBuilder();
                    ulong parentId = (page.ID == homepageId) ? 0 : page.ID;
                    foreach (NavBE child in list)
                    {
                        if ((child.ParentId == parentId) && (child.Id != homepageId))
                        {
                            if (nodes.Length != 0)
                            {
                                nodes.Append(",");
                            }
                            nodes.AppendFormat("n{0}", child.Id);
                        }
                    }
                    result.Elem("nodes", nodes.ToString());

                    // add <div> list
                    result.Start("html");
                    if (exclude != 0)
                    {
                        result.Elem("pre", doc["children-pre"].Contents);
                        result.Elem("post", doc["children-post"].Contents);
                    }
                    else
                    {
                        result.Value(doc["children-post"].Contents);
                    }
                    result.End();
                    result.End();
                    response.Return(DreamMessage.Ok(result));
                }
            }
            yield break;
        }
Esempio n. 37
0
        //--- Methods ---
        private void AddFunction(XDoc result, string ns, XDoc function) {
            result.Start("blockquote");
            List<Tuplet<string, bool, string, string>> args = new List<Tuplet<string, bool, string, string>>();
            StringBuilder signature = new StringBuilder();
            signature.Append(((ns != null) ? ns + "." : string.Empty) + function["name"].AsText);
            if(string.IsNullOrEmpty(function["@usage"].AsText)) {
                signature.Append("(");

                // enumerate arguments
                int count = 1;
                foreach(XDoc arg in function["param"]) {

                    // add argument to signature
                    if(count > 1) {
                        signature.Append(", ");
                    }
                    string name = arg["@name"].AsText ?? arg["name"].AsText ?? ("arg" + count.ToString());
                    signature.Append(name);
                    string type = arg["@type"].AsText ?? arg["type"].AsText;
                    if(type != null) {
                        signature.Append(" : ");
                        signature.Append(type);
                    }
                    ++count;

                    // add argument to explanation
                    if(!arg["hint"].IsEmpty || !string.IsNullOrEmpty(arg.AsText)) {
                        args.Add(new Tuplet<string, bool, string, string>(name, StringUtil.EqualsInvariant(arg["@optional"].AsText, "true") || !arg["@default"].IsEmpty || !arg["hint[@optional='true']"].IsEmpty, arg["hint"].AsText ?? arg.AsText, arg["@default"].AsText));
                    }
                }
                signature.Append(")");
            }
            signature.Append(" : ").Append(function["return/@type"].AsText ?? "any");
            result.Elem("h3", signature.ToString());
            if(function["description"].AsText != null) {
                result.Elem("p", function["description"].AsText);
            }

            // add argument explanation
            if(args.Count > 0) {
                result.Start("ul");
                foreach(Tuplet<string, bool, string, string> arg in args) {
                    result.Start("li");
                    result.Elem("strong", arg.Item1);
                    if(arg.Item2) {
                        result.Value(" (optional)");
                    }
                    result.Value(": " + arg.Item3);
                    if(arg.Item4 != null) {
                        result.Value(" (default: " + arg.Item4 + ")");
                    }
                    result.End();
                }
                result.End();
            }
            result.Elem("br");
            result.End();
        }
Esempio n. 38
0
        //--- Class Methods ---
        public static ServiceBE StartService(ServiceBE service, bool forceRefresh, bool disableOnFailure)
        {
            // create subordinate request id for service start
            var dreamContext = DreamContext.Current;
            var requestId    = dreamContext.GetState <string>(DreamHeaders.DREAM_REQUEST_ID);

            dreamContext.SetState(DreamHeaders.DREAM_REQUEST_ID, requestId + "-service_" + service.Id);

            try {
                var stopwatch = Stopwatch.StartNew();
                service.ServiceLastStatus = string.Empty;
                StopService(service.Id, service, ServiceStopType.Restart);
                DekiContext context            = DekiContext.Current;
                bool        dirtyServiceEntity = false;
                XUri        location;
                ServiceRepository.IServiceInfo serviceInfo = null;
                try {
                    // check if service is local
                    if (service.ServiceLocal)
                    {
                        if (string.IsNullOrEmpty(service.SID))
                        {
                            throw new Exception("missing SID");
                        }

                        // start service
                        if (IsLocalAuthService(service))
                        {
                            // this service is the built-in authentication provider; no need to start it
                            location = context.Deki.Self;
                        }
                        else
                        {
                            // convert local service configuration into an xdoc
                            XDoc config = new XDoc("config");
                            foreach (KeyValuePair <string, string> configEntry in ArrayUtil.AllKeyValues(service.Config))
                            {
                                config.InsertValueAt(configEntry.Key, configEntry.Value);
                            }

                            // if no apikey was provided, create a random one so that CreateService doesn't inject the parent one
                            if (config["apikey"].IsEmpty)
                            {
                                config.Elem("apikey", StringUtil.CreateAlphaNumericKey(16));
                            }

                            // add information for service to callback into deki
                            if (config["uri.deki"].IsEmpty)
                            {
                                config.Elem("uri.deki", context.Deki.Self);
                                config.Elem("wikiid.deki", context.Instance.Id);

                                // Providing master apikey to service for setups that don't use per instance keys
                                config.Elem("apikey.deki", context.Instance.ApiKey.IfNullOrEmpty(context.Deki.MasterApiKey));
                            }

                            // the service location must use the service ID and the instance ID
                            string servicePath = string.Format("services/{0}/{1}", context.Instance.Id, service.Id);
                            _log.DebugFormat("starting service '{0}' at path {1} w/ namespace {2}", service.SID, servicePath, service.Preferences["namespace"]);
                            serviceInfo = context.Instance.CreateLocalService(service, servicePath, config);
                            location    = serviceInfo.ServiceUri;
                        }

                        // check if the service uri has changed since last invocation (happens when service is started for the first time or server GUID has changed)
                        if (!service.Uri.EqualsInvariantIgnoreCase(location.ToString()))
                        {
                            dirtyServiceEntity = true;
                            service.Uri        = location.ToString();
                        }
                    }
                    else
                    {
                        _log.DebugFormat("registering remote service '{0}'", service.SID);
                        if (string.IsNullOrEmpty(service.Uri))
                        {
                            throw new Exception("missing URI");
                        }
                        location    = new XUri(service.Uri);
                        serviceInfo = context.Instance.RegisterRemoteService(service, location);
                    }

                    // check if service is an Extension service
                    if (service.Type == ServiceType.EXT)
                    {
                        if (service.ServiceLocal)
                        {
                            _log.DebugFormat("registering service '{0}' as extension", service.SID);
                        }
                        ExtensionBL.StartExtensionService(context, service, serviceInfo, forceRefresh);
                    }

                    //Successfully starting a service enables it.
                    if (!service.ServiceEnabled)
                    {
                        dirtyServiceEntity     = true;
                        service.ServiceEnabled = true;
                    }
                } catch (Exception e) {
                    dirtyServiceEntity = true;
                    DreamMessage dm = null;
                    if (e is DreamResponseException)
                    {
                        dm = ((DreamResponseException)e).Response;
                        string message = dm.HasDocument ? dm.ToDocument()[".//message"].AsText.IfNullOrEmpty(e.Message) : dm.ToText();
                        service.ServiceLastStatus = string.Format("unable to initialize service ({0})", message);
                    }
                    else
                    {
                        service.ServiceLastStatus = e.GetCoroutineStackTrace();
                    }
                    if (serviceInfo != null)
                    {
                        try {
                            context.Instance.DeregisterService(service.Id);
                        } catch { }
                    }

                    // A service that fails to start becomes disabled if it's started explicitly (not during deki startup)
                    if (disableOnFailure)
                    {
                        service.ServiceEnabled = false;
                    }
                    _log.ErrorExceptionMethodCall(e, "StartService", string.Format("Unable to start local service id '{0}' with SID '{1}' Error: '{2}'", service.Id, service.SID, service.ServiceLastStatus));
                    if (dm != null)
                    {
                        throw new ExternalServiceResponseException(dm);
                    }
                    else
                    {
                        throw;
                    }
                } finally {
                    // don't update remote services that haven't changed
                    if (dirtyServiceEntity)
                    {
                        service = UpdateService(service);
                    }
                }
                stopwatch.Stop();
                _log.InfoFormat("Service '{0}' ({1}) started in {2}ms", service.Description, service.SID, stopwatch.ElapsedMilliseconds);
                return(service);
            } finally {
                // restore the request id
                dreamContext.SetState(DreamHeaders.DREAM_REQUEST_ID, requestId);
            }
        }
Esempio n. 39
0
        public Yield GetSiteFunctions(DreamContext context, DreamMessage request, Result<DreamMessage> response) {
            PermissionsBL.CheckUserAllowed(DekiContext.Current.User, Permissions.UPDATE);

            // build set of libraries
            List<XDoc> libraries = DekiContext.Current.Instance.RunningServices.ExtensionServices
                .Select(x => x.Extension.Manifest).ToList();

            // add registered libraries
            libraries.Sort((left, right) => left["title"].Contents.CompareInvariantIgnoreCase(right["title"].Contents));

            // add built-in functions
            XDoc builtinlib = new XDoc("extension");
            builtinlib.Elem("title", "Built-in Functions");
            builtinlib.Elem("label", "Built-in");
            builtinlib.Elem("uri.help", "http://wiki.developer.mindtouch.com/MindTouch_Deki/DekiScript/Reference");
            builtinlib.Elem("description", "The following functions and variables are part the DekiScript and MindTouch runtime environment.");
            foreach(var function in ScriptRuntime.Functions.Values) {
                if(function.Access == DreamAccess.Public) {
                    builtinlib.Add(function.ToXml(null));
                }
            }
            libraries.Insert(0, builtinlib);

            // create composite document
            bool hasUnsafeContentPermission = PermissionsBL.IsUserAllowed(DekiContext.Current.User, Permissions.UNSAFECONTENT);
            XDoc extensions = new XDoc("extensions").AddAll(libraries);
            foreach(XDoc extension in extensions["extension"]) {
                XUri serviceUri = extension["@uri"].AsUri;

                // check if extension is protected
                bool @protected;
                bool.TryParse(ExtensionBL.GetExtensionPreference(serviceUri, "protected"), out @protected);
                if(@protected) {
                    if(!hasUnsafeContentPermission) {
                        extension.Remove();
                        continue;
                    }
                    extension.Attr("protected", @protected);
                }

                // read overwriteable settings
                AddOrReplace(extension, "title", ExtensionBL.GetExtensionPreference(serviceUri, "title.custom"));
                AddOrReplace(extension, "uri.logo", ExtensionBL.GetExtensionPreference(serviceUri, "uri.logo.custom"));
                AddOrReplace(extension, "namespace", ExtensionBL.GetExtensionPreference(serviceUri, "namespace.custom"));
                extension.Elem("description.custom", ExtensionBL.GetExtensionPreference(serviceUri, "description.custom"));

                // check which functions to keep
                string[] allowedFunctions = (ExtensionBL.GetExtensionPreference(serviceUri, "functions") ?? string.Empty).Split(new char[] { ' ', ',' }, StringSplitOptions.RemoveEmptyEntries);
                if(allowedFunctions.Length > 0) {
                    foreach(XDoc function in extension["function"]) {

                        // check if user specified a list of functions to show
                        string name = function["name"].Contents;
                        if(Array.FindIndex(allowedFunctions, current => current.EqualsInvariantIgnoreCase(name)) < 0) {
                            function.Remove();
                        }
                    }
                }

                // check if extension has any functions
                if(extension["function"].ListLength == 0) {
                    extension.Remove();
                }
            }

            // build response document
            string format = context.GetParam("format", "html");
            if(StringUtil.EqualsInvariant(format, "xml")) {
                response.Return(DreamMessage.Ok(extensions));
            } else {

                // prepare document
                string header = string.Format("{0} - Registered Extensions", DekiContext.Current.Instance.SiteName);
                XDoc result = new XDoc("html").Attr("xmlns", "http://www.w3.org/1999/xhtml")
                    .Start("head")
                        .Elem("title", header)
                        .Start("meta").Attr("http-equiv", "content-type").Attr("content", "text/html;charset=utf-8").End()
                    .End();
                result.Start("body");
                result.Elem("h1", header);

                // build table of contents
                result.Elem("strong", "Table of Contents");
                result.Start("ol");
                int count = 0;
                foreach(XDoc library in extensions["extension"]) {
                    ++count;
                    XUri serviceUri = library["@uri"].AsUri;
                    result.Start("li").Start("a").Attr("href", "#section" + count).Value(ExtensionBL.GetExtensionPreference(serviceUri, "title.custom") ?? library["title"].AsText).End().End();
                }
                result.End();

                // enumerate libraries
                count = 0;
                foreach(XDoc library in extensions["extension"]) {
                    ++count;

                    // read overwriteable settings
                    string title = library["title"].AsText;
                    string logo = library["uri.logo"].AsText;
                    string ns = library["namespace"].AsText;
                    bool @protected = library["@protected"].AsBool ?? false;

                    // show & link library name
                    result.Start("h2").Attr("id", "section" + count);
                    if(!string.IsNullOrEmpty(library["uri.help"].AsText)) {
                        result.Start("a").Attr("href", library["uri.help"].AsText).Attr("target", "_blank").Attr("title", library["title"].AsText + " Documentation").Value(title).End();
                    } else {
                        result.Value(title);
                    }
                    if(@protected) {
                        result.Value(string.Format(" ({0})", DekiResources.PROTECTED));
                    }
                    result.End();

                    // show optional logo
                    if(!string.IsNullOrEmpty(logo)) {
                        result.Start("img").Attr("src", logo).Attr("alt", title).End();
                    }

                    // show descriptions
                    if(library["uri.license"].AsText != null) {
                        result.Start("a").Attr("href", library["uri.license"].AsText).Attr("target", "_blank").Value("Read Library License").End();
                    }
                    if(!string.IsNullOrEmpty(library["description"].AsText)) {
                        result.Elem("p", library["description"].AsText);
                    }
                    if(!string.IsNullOrEmpty(library["description.custom"].AsText)) {
                        result.Elem("p", library["description.custom"].AsText);
                    }

                    // enumerate library functions
                    XDoc functions = new XDoc("functions").AddAll(library["function"]);
                    functions.Sort(delegate(XDoc left, XDoc right) {
                        return StringUtil.CompareInvariantIgnoreCase(left["name"].Contents, right["name"].Contents);
                    });
                    foreach(XDoc function in functions["function"]) {
                        AddFunction(result, ns, function);
                    }
                }
                result.End();
                switch(format) {
                default:
                case "html":
                    response.Return(DreamMessage.Ok(MimeType.HTML, result.ToString()));
                    break;
                case "body":
                    response.Return(DreamMessage.Ok(MimeType.TEXT_UTF8, result["body"].Contents));
                    break;
                }
            }
            yield break;
        }
 public static XDoc Heading(this XDoc doc, int level, string value)
 {
     return(doc.Elem("H" + (level + 1), value));
 }
Esempio n. 41
0
        private XDoc BuildBugListHTMLTable(RemoteIssue[] issues)
        {
            XDoc ret = new XDoc("div").Attr("class", "DW-table Jira-table table");

            ret.Start("table").Attr("border", 0).Attr("cellspacing", 0).Attr("cellpadding", 0).Attr("class", "table feedtable sortable");

            // header
            ret.Start("tr")
            .Elem("th", "Bug#")
            .Elem("th", "Summary")
            .Elem("th", "Status")
            .Elem("th", "Priority")
            .Elem("th", "Opened By")
            .Elem("th", "Assigned To")

            .End();


            int count = 0;

            foreach (RemoteIssue bug in issues)
            {
                count++;
                RemoteStatus status = null;
                if (!string.IsNullOrEmpty(bug.status))
                {
                    _statuses.TryGetValue(bug.status, out status);
                }

                RemotePriority priority = null;
                if (!string.IsNullOrEmpty(bug.priority))
                {
                    _priorities.TryGetValue(bug.priority, out priority);
                }

                string trClass = string.Format("{0} {1}", (count % 2 == 0) ? "even" : "odd", status == null ? string.Empty : status.name);
                ret.Start("tr").Attr("class", trClass);
                ret.Start("td");
                ret = BuildBugLink(bug, ret);
                ret.End(); //td;
                ret.Elem("td", bug.summary);
                if (status == null)
                {
                    ret.Elem("td", "");
                }
                else
                {
                    ret.Start("td").Start("img").Attr("src", status.icon).Attr("alt", status.name).Attr("title", status.description).End().Value(status.name).End();
                }

                if (priority == null)
                {
                    ret.Elem("td");
                }
                else
                {
                    ret.Start("td").Start("img").Attr("src", priority.icon).Attr("alt", priority.name).Attr("title", priority.description).End().Value(priority.name).End();
                }

                ret.Elem("td", bug.reporter ?? string.Empty);
                ret.Elem("td", bug.assignee ?? string.Empty);

                ret.End(); //tr
            }
            ret.End();     // table
            return(ret);
        }
Esempio n. 42
0
        //--- Class Methods ---
        /// <summary>
        /// Create a service blueprint from reflection and attribute meta-data for an <see cref="IDreamService"/> implementation.
        /// </summary>
        /// <param name="type">Type of examine.</param>
        /// <returns>Xml formatted blueprint.</returns>
        public static XDoc CreateServiceBlueprint(Type type)
        {
            if(type == null) {
                throw new ArgumentNullException("type");
            }
            XDoc result = new XDoc("blueprint");

            // load assembly
            Dictionary<string, string> assemblySettings = new Dictionary<string, string>(StringComparer.Ordinal);
            string[] assemblyParts = type.Assembly.FullName.Split(',');
            foreach(string parts in assemblyParts) {
                string[] assign = parts.Trim().Split(new char[] { '=' }, 2);
                if(assign.Length == 2) {
                    assemblySettings[assign[0].Trim()] = assign[1].Trim();
                }
            }
            result.Start("assembly");
            foreach(KeyValuePair<string, string> entry in assemblySettings) {
                result.Attr(entry.Key, entry.Value);
            }
            result.Value(assemblyParts[0]);
            result.End();
            result.Elem("class", type.FullName);

            // retrieve DreamService attribute on class definition
            DreamServiceAttribute serviceAttrib = (DreamServiceAttribute)Attribute.GetCustomAttribute(type, typeof(DreamServiceAttribute), false);
            result.Elem("name", serviceAttrib.Name);
            result.Elem("copyright", serviceAttrib.Copyright);
            result.Elem("info", serviceAttrib.Info);

            // retrieve DreamServiceUID attributes
            foreach(XUri sid in serviceAttrib.GetSIDAsUris()) {
                result.Elem("sid", sid);
            }

            // check if service has blueprint settings
            foreach(DreamServiceBlueprintAttribute blueprintAttrib in Attribute.GetCustomAttributes(type, typeof(DreamServiceBlueprintAttribute), true)) {
                result.InsertValueAt(blueprintAttrib.Name, blueprintAttrib.Value);
            }

            // check if service has configuration information
            DreamServiceConfigAttribute[] configAttributes = (DreamServiceConfigAttribute[])Attribute.GetCustomAttributes(type, typeof(DreamServiceConfigAttribute), true);
            if(!ArrayUtil.IsNullOrEmpty(configAttributes)) {
                result.Start("configuration");
                foreach(DreamServiceConfigAttribute configAttr in configAttributes) {
                    result.Start("entry")
                        .Elem("name", configAttr.Name)
                        .Elem("valuetype", configAttr.ValueType)
                        .Elem("description", configAttr.Description)
                    .End();
                }
                result.End();
            }

            // retrieve DreamFeature attributes on method definitions
            result.Start("features");
            MethodInfo[] methods = type.GetMethods(BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic);
            foreach(MethodInfo method in methods) {

                // retrieve feature description
                Attribute[] featureAttributes = Attribute.GetCustomAttributes(method, typeof(DreamFeatureAttribute), false);
                if(featureAttributes.Length == 0) {
                    continue;
                }
                if(method.IsGenericMethod || method.IsGenericMethodDefinition) {
                    throw new NotSupportedException(string.Format("generic methods are not supported ({0})", method.Name));
                }

                // determine access level
                string access;
                if(method.IsPublic) {
                    access = "public";
                } else if(method.IsAssembly) {
                    access = "internal";
                } else if(method.IsPrivate || method.IsFamily) {
                    access = "private";
                } else {
                    throw new NotSupportedException(string.Format("access level is not supported ({0})", method.Name));
                }

                // retrieve feature parameter descriptions, filters, prologues, and epilogues
                Attribute[] paramAttributes = Attribute.GetCustomAttributes(method, typeof(DreamFeatureParamAttribute), false);
                var pathAttributes = method.GetParameters().Select(p => {
                    var attr = (PathAttribute)p.GetCustomAttributes(typeof(PathAttribute), false).FirstOrDefault();
                    return ((attr != null) && (attr.Name == null)) ? new PathAttribute { Description = attr.Description, Name = p.Name } : attr;
                }).Where(p => p != null);
                var queryAttributes = method.GetParameters().Select(q => {
                    var attr = (QueryAttribute)q.GetCustomAttributes(typeof(QueryAttribute), false).FirstOrDefault();
                    return ((attr != null) && (attr.Name == null)) ? new QueryAttribute { Description = attr.Description, Name = q.Name } : attr;
                }).Where(q => q != null);
                Attribute[] statusAttributes = Attribute.GetCustomAttributes(method, typeof(DreamFeatureStatusAttribute), false);
                foreach(DreamFeatureAttribute featureAttrib in featureAttributes) {
                    result.Start("feature");
                    result.Elem("obsolete", featureAttrib.Obsolete);
                    result.Elem("pattern", featureAttrib.Pattern);
                    result.Elem("description", featureAttrib.Description);
                    string info = featureAttrib.Info ?? serviceAttrib.Info;
                    if(info != null) {
                        result.Elem("info", info);
                    }
                    result.Elem("method", method.Name);

                    // add parameter descriptions (as seen on the method definition)
                    foreach(DreamFeatureParamAttribute paramAttrib in paramAttributes) {
                        result.Start("param");
                        result.Elem("name", paramAttrib.Name);
                        if(!string.IsNullOrEmpty(paramAttrib.ValueType)) {
                            result.Elem("valuetype", paramAttrib.ValueType);
                        }
                        result.Elem("description", paramAttrib.Description);
                        result.End();
                    }

                    // add parameter descriptions (as seen on the method parameters)
                    foreach(PathAttribute pathAttrib in pathAttributes) {
                        result.Start("param")
                            .Elem("name", "{" + pathAttrib.Name + "}")
                            .Elem("description", pathAttrib.Description)
                        .End();
                    }

                    // add parameter descriptions (as seen on the method parameters)
                    foreach(QueryAttribute queryAttrib in queryAttributes) {
                        result.Start("param")
                            .Elem("name", queryAttrib.Name)
                            .Elem("description", queryAttrib.Description)
                        .End();
                    }

                    // add status codes
                    foreach(DreamFeatureStatusAttribute paramAttrib in statusAttributes) {
                        result.Start("status");
                        result.Attr("value", (int)paramAttrib.Status);
                        result.Value(paramAttrib.Description);
                        result.End();
                    }

                    // add access level
                    result.Elem("access", access);
                    result.End();
                }
            }
            result.End();
            return result.EndAll();
        }
Esempio n. 43
0
        public Yield ValidateOpenIdResponse(DreamContext context, DreamMessage request, Result<DreamMessage> response) {
            XUri publicUri = new XUri(context.GetParam("url", null));
            NameValueCollection queryColl = System.Web.HttpUtility.ParseQueryString(context.GetParam("query", null));

            // process the response, including validating the endpoint of the claimed identifier.
            OpenIdRelyingParty openid = new OpenIdRelyingParty(null, publicUri, queryColl);
            var openIdResponse = openid.Response;

            if (openIdResponse != null) {
                switch (openIdResponse.Status) {
                    case AuthenticationStatus.Authenticated:
                       
                        // Throw an exception if there is a regex for acceptable
                        // identifiers defined, and the ID does not match.
                        if (!String.IsNullOrEmpty(_validIdPattern)) {
                            Regex identifierAccept = new Regex(_validIdPattern);
                            if (!identifierAccept.IsMatch(openIdResponse.ClaimedIdentifier)) {
                                _log.InfoFormat("Identifier {0} denied access by valid-id-pattern regular expression {1}", openIdResponse.ClaimedIdentifier, _validIdPattern);
                                throw new DreamBadRequestException("This service is configured to deny access to this OpenID identifier.");
                            }
                        }

                        var claimsResponse = openIdResponse.GetExtension<ClaimsResponse>();
                        var fetchResponse = openIdResponse.GetExtension<FetchResponse>();

                        XDoc result = new XDoc("openid");
                        result.Attr("validated", true);
                        result.Elem("identifier", openIdResponse.ClaimedIdentifier);
			
                        // SREG response
                        if (claimsResponse != null) {
                            string email = claimsResponse.Email;
                            if (email != null) {
                                result.Elem("email", email);
                                _log.DebugFormat("E-mail address from SREG: {0}", email);
                            }
                        }
                        // AX response
                        if (fetchResponse != null) {
                            foreach (AttributeValues v in fetchResponse.Attributes) {
                                if (v.TypeUri == WellKnownAttributes.Contact.Email) {
                                    IList<string> emailAddresses = v.Values;
                                    string email = emailAddresses.Count > 0 ? emailAddresses[0] : null;
                                    result.Elem("email", email);
                                    _log.DebugFormat("E-mail address from AX: {0}", email);
                                }
                            }
                        }
                        response.Return(DreamMessage.Ok(result));
                        break;
                    case AuthenticationStatus.Canceled:
                        _log.InfoFormat("Authentication was cancelled by the user.");
                        throw new DreamBadRequestException("Authentication was cancelled by the user.");
                    case AuthenticationStatus.Failed:
                        _log.InfoFormat("Authentication failed: " + openIdResponse.Exception.Message);
                        throw new DreamBadRequestException("Authentication failed: " + openIdResponse.Exception.Message);
                    default:
                        _log.WarnFormat("Authentication error: " + openIdResponse.Exception.Message);
                        throw new DreamBadRequestException("Authentication error: " + openIdResponse.Exception.Message);
                }
            } else {
                _log.Warn("OpenID response was null");
                throw new DreamBadRequestException("No OpenID response was returned.");
            }
            yield break;
        }      
Esempio n. 44
0
        private void LoadGroups(string tMainWebWikiDataPath)
        {
            foreach (string groupFileName in Directory.GetFiles(tMainWebWikiDataPath, "*Group.txt"))
            {
                string groupName = Path.GetFileNameWithoutExtension(Path.GetFileName(groupFileName));
                
                string groupContent = File.ReadAllText(groupFileName);

                TWikiGroup group = null;
                _convertedGroups.TryGetValue(groupName, out group);
                if (group == null)
                {
                    group = new TWikiGroup(true, groupName);
                }

                string[] members = ExtractNamesList(groupContent, "GROUP");

                foreach (string member in members)
                {
                    group.AddMemeber(member);
                }

                _convertedGroups[groupName] = group;
            }

            DreamMessage msg = _dekiPlug.At("groups").With("limit", int.MaxValue).GetAsync().Wait();
            if (msg.Status != DreamStatus.Ok)
            {
                WriteErrorResponse(msg, "Error while reciving groups from Deki. Groups not converted.");
                return;
            }
            Dictionary<string, string> dekiGroups = new Dictionary<string, string>(StringComparer.InvariantCultureIgnoreCase);

            XDoc groupsDoc = msg.AsDocument();
            foreach (XDoc groupDoc in groupsDoc["//group"])
            {
                string dekiGroupName = groupDoc["groupname"].AsText;
                dekiGroups[dekiGroupName.ToLower()] = null;
            }

            foreach (string groupName in _convertedGroups.Keys)
            {
                TWikiGroup group = _convertedGroups[groupName];
                if (group.IsNewGroup)
                {
                    int groupNum = 0;
                    string dekiGroupName = groupName;
                    while (dekiGroups.ContainsKey(dekiGroupName))
                    {
                        groupNum++;
                        dekiGroupName = groupName + groupNum.ToString();
                    }
                    if (dekiGroupName != groupName)
                    {
                        WriteLineToConsole("TWiki group \"" + groupName + "\" converted as \"" + dekiGroupName + "\" becouse of existing same group in Deki");
                    }
                    group.DekiName = dekiGroupName;

                    XDoc newGroupDoc = new XDoc("group");
                    newGroupDoc.Elem("name", group.DekiName);

                    TWikiUser[] members = GetAllGroupMembers(groupName);
                    if (members.Length > 0)
                    {
                        newGroupDoc.Start("users");
                        foreach (TWikiUser member in members)
                        {
                            newGroupDoc.Start("user").Attr("id", member.DekiId).End();
                        }
                        newGroupDoc.End();
                    }

                    DreamMessage res = _dekiPlug.At("groups").PostAsync(newGroupDoc).Wait();
                    WriteErrorResponse(res, "Error converting group\"" + groupName + "\"");
                }
                else
                {
                    XDoc updateGroupDoc = new XDoc("users");
                    TWikiUser[] members = GetAllGroupMembers(groupName);
                    if (members.Length > 0)
                    {
                        foreach (TWikiUser member in members)
                        {
                            updateGroupDoc.Start("user").Attr("id", member.DekiId).End();
                        }
                    }
                    DreamMessage res = _dekiPlug.At("groups", "=" + group.DekiName, "users").PutAsync(updateGroupDoc).Wait();
                    WriteErrorResponse(res, "Error updating group \"" + groupName + "\" users.");
                }
            }
        }
Esempio n. 45
0
        private static XDoc QueryPageVersions(ulong pageId, int? afterRevision, int? beforeRevision, IDictionary<string, XDoc> cache) {
            XDoc doc = new XDoc("diff");

            // retrieve 'after' version
            if(afterRevision.HasValue) {
                XDoc contents;
                string key = string.Format("{0}-{1}", pageId, afterRevision);

                // chek if we have a cached version
                if(!cache.TryGetValue(key, out contents)) {

                    // store response (doesn't matter if it was successful or not)
                    cache[key] = contents = GetParsedPageRevision(pageId, afterRevision.Value);
                }
                if(contents != null) {
                    doc.Start("after").Start("body");
                    doc.Elem("h1", contents["@title"].AsText);
                    doc.AddNodes(contents["body"]);
                    doc.End().End();
                }
            }

            // check if 'before' version is expected to be different
            if(beforeRevision.HasValue && (afterRevision != beforeRevision) && (beforeRevision > 0)) {
                XDoc contents;
                string key = string.Format("{0}-{1}", pageId, beforeRevision);

                // chek if we have a cached version
                if(!cache.TryGetValue(key, out contents)) {

                    // store response (doesn't matter if it was successful or not)
                    cache[key] = contents = GetParsedPageRevision(pageId, beforeRevision.Value);
                }
                if(contents != null) {
                    doc.Start("before").Start("body");
                    doc.Elem("h1", contents["@title"].AsText);
                    doc.AddNodes(contents["body"]);
                    doc.End().End();
                }
            }
            return doc;
        }
        //--- Class Methods ---
        private static void XmlRpcLiteralRecurse(XDoc xdoc, DekiScriptLiteral value, bool isArgumentList)
        {
            if (!isArgumentList)
            {
                xdoc.Start("value");
            }
            switch (value.ScriptType)
            {
            case DekiScriptType.BOOL:
                xdoc.Elem("boolean", ((DekiScriptBool)value).Value ? "1" : "0");
                break;

            case DekiScriptType.NUM:
                xdoc.Elem("double", ((DekiScriptNumber)value).Value);
                break;

            case DekiScriptType.STR:
                xdoc.Elem("string", ((DekiScriptString)value).Value); // in order to work with php, this may need to be encoded
                break;

            case DekiScriptType.NIL:
                xdoc.Elem("nil");
                break;

            case DekiScriptType.URI:
                xdoc.Start("string").Attr("type", "uri").End();
                break;

            case DekiScriptType.XML:
                xdoc.Start("string").Attr("type", "xml").Value(value.NativeValue.ToString()).End();
                break;

            case DekiScriptType.LIST:
                xdoc.Start(isArgumentList ? "params" : "array");
                if (!isArgumentList)
                {
                    xdoc.Start("data");
                }
                foreach (DekiScriptLiteral entry in ((DekiScriptList)value).Value)
                {
                    if (isArgumentList)
                    {
                        xdoc.Start("param");
                        XmlRpcLiteralRecurse(xdoc, entry, false);
                        xdoc.End();
                    }
                    else
                    {
                        XmlRpcLiteralRecurse(xdoc, entry, false);
                    }
                }
                if (!isArgumentList)
                {
                    xdoc.End();
                }
                xdoc.End();
                break;

            case DekiScriptType.MAP:
                xdoc.Start("struct");
                foreach (KeyValuePair <string, DekiScriptLiteral> entry in ((DekiScriptMap)value).Value)
                {
                    xdoc.Start("member");
                    xdoc.Elem("name", entry.Key);
                    XmlRpcLiteralRecurse(xdoc, entry.Value, false);
                    xdoc.End();
                }
                xdoc.End();
                break;

            default:
                throw new ShouldNeverHappenException("unkwown type");
            }
            if (!isArgumentList)
            {
                xdoc.End();
            }
            return;
        }
Esempio n. 47
0
        public virtual Yield GetServiceInfo(DreamContext context, DreamMessage request, Result<DreamMessage> response)
        {
            XDoc blueprint = Blueprint;
            string title = blueprint["name"].AsText ?? "Service Blueprint";
            XDoc result = new XDoc("html").Attr("xmlns", "http://www.w3.org/1999/xhtml")
                .Start("head")
                    .Elem("title", title)
                    .Start("meta").Attr("http-equiv", "content-type").Attr("content", "text/html;charset=utf-8").End()
                    .Start("meta").Attr("http-equiv", "Content-Style-Type").Attr("content", "text/css").End()
                .End();
            if(blueprint.IsEmpty) {
                result.Elem("body", "Missing service blueprint");
            } else {
                result.Start("body")
                        .Elem("h1", title)
                        .Start("p")
                            .Value(blueprint["copyright"].Contents)
                            .Value(" ")
                            .Start("a").Attr("href", blueprint["info"].Contents).Value("(more)").End()
                            .Value(" ")
                            .Start("a").Attr("href", Self.Uri.At("@blueprint").Path).Value("(blueprint)").End()
                        .End();

                // show configuration information
                XDoc config = blueprint["configuration"];
                if(!config.IsEmpty) {
                    result.Elem("h2", "Configuration");
                    result.Start("ul");
                    foreach(XDoc entry in config["entry"]) {
                        result.Start("li");
                        if(entry["valuetype"].Contents != string.Empty) {
                            result.Value(string.Format("{0} = {1} : {2}", entry["name"].Contents, entry["valuetype"].Contents, entry["description"].Contents));
                        } else {
                            result.Value(string.Format("{0} : {1}", entry["name"].Contents, entry["description"].Contents));
                        }
                        result.End();
                    }
                    result.End();
                }

                // sort features by signature then verb
                blueprint["features"].Sort(delegate(XDoc first, XDoc second) {
                    string[] firstPattern = first["pattern"].Contents.Split(new[] { ':' }, 2);
                    string[] secondPattern = second["pattern"].Contents.Split(new[] { ':' }, 2);
                    int cmp = firstPattern[1].CompareInvariantIgnoreCase(secondPattern[1]);
                    if(cmp != 0) {
                        return cmp;
                    }
                    return firstPattern[0].CompareInvariant(secondPattern[0]);
                });

                // display features
                XDoc features = blueprint["features/feature"];
                if(!features.IsEmpty) {
                    result.Elem("h2", "Features");
                    List<string> modifiers = new List<string>();
                    foreach(XDoc feature in features) {
                        modifiers.Clear();

                        // add modifiers
                        string modifier = feature["access"].AsText;
                        if(modifier != null) {
                            modifiers.Add(modifier);
                        }
                        modifier = feature["obsolete"].AsText;
                        if(modifier != null) {
                            modifiers.Add("OBSOLETE => " + modifier);
                        }
                        if(modifiers.Count > 0) {
                            modifier = " (" + string.Join(", ", modifiers.ToArray()) + ")";
                        } else {
                            modifier = string.Empty;
                        }

                        // check if feature has GET verb and no path parameters
                        string pattern = feature["pattern"].Contents;
                        if(pattern.StartsWithInvariantIgnoreCase(Verb.GET + ":") && (pattern.IndexOfAny(new[] { '{', '*', '?' }) == -1)) {
                            string[] parts = pattern.Split(new[] { ':' }, 2);
                            result.Start("h3")
                                .Start("a").Attr("href", context.AsPublicUri(Self.Uri.AtPath(parts[1])))
                                    .Value(feature["pattern"].Contents)
                                .End()
                                .Value(modifier)
                            .End();
                        } else {
                            result.Elem("h3", feature["pattern"].Contents + modifier);
                        }
                        result.Start("p")
                                .Value(feature["description"].Contents)
                                .Value(" ")
                                .Start("a").Attr("href", feature["info"].Contents).Value("(more)").End();
                        XDoc paramlist = feature["param"];
                        if(!paramlist.IsEmpty) {
                            result.Start("ul");
                            foreach(XDoc param in paramlist) {
                                result.Start("li");
                                if(param["valuetype"].Contents != string.Empty) {
                                    result.Value(string.Format("{0} = {1} : {2}", param["name"].Contents, param["valuetype"].Contents, param["description"].Contents));
                                } else {
                                    result.Value(string.Format("{0} : {1}", param["name"].Contents, param["description"].Contents));
                                }
                                result.End();
                            }
                            result.End();
                        }
                        result.End();
                    }
                }
            }
            response.Return(DreamMessage.Ok(MimeType.HTML, result.ToString()));
            yield break;
        }
Esempio n. 48
0
        public Yield ValidateOpenIdResponse(DreamContext context, DreamMessage request, Result <DreamMessage> response)
        {
            XUri publicUri = new XUri(context.GetParam("url", null));
            NameValueCollection queryColl = System.Web.HttpUtility.ParseQueryString(context.GetParam("query", null));

            // process the response, including validating the endpoint of the claimed identifier.
            OpenIdRelyingParty openid = new OpenIdRelyingParty(null, publicUri, queryColl);
            var openIdResponse        = openid.Response;

            if (openIdResponse != null)
            {
                switch (openIdResponse.Status)
                {
                case AuthenticationStatus.Authenticated:

                    // Throw an exception if there is a regex for acceptable
                    // identifiers defined, and the ID does not match.
                    if (!String.IsNullOrEmpty(_validIdPattern))
                    {
                        Regex identifierAccept = new Regex(_validIdPattern);
                        if (!identifierAccept.IsMatch(openIdResponse.ClaimedIdentifier))
                        {
                            _log.InfoFormat("Identifier {0} denied access by valid-id-pattern regular expression {1}", openIdResponse.ClaimedIdentifier, _validIdPattern);
                            throw new DreamBadRequestException("This service is configured to deny access to this OpenID identifier.");
                        }
                    }

                    var claimsResponse = openIdResponse.GetExtension <ClaimsResponse>();
                    var fetchResponse  = openIdResponse.GetExtension <FetchResponse>();

                    XDoc result = new XDoc("openid");
                    result.Attr("validated", true);
                    result.Elem("identifier", openIdResponse.ClaimedIdentifier);

                    // SREG response
                    if (claimsResponse != null)
                    {
                        string email = claimsResponse.Email;
                        if (email != null)
                        {
                            result.Elem("email", email);
                            _log.DebugFormat("E-mail address from SREG: {0}", email);
                        }
                    }
                    // AX response
                    if (fetchResponse != null)
                    {
                        foreach (AttributeValues v in fetchResponse.Attributes)
                        {
                            if (v.TypeUri == WellKnownAttributes.Contact.Email)
                            {
                                IList <string> emailAddresses = v.Values;
                                string         email          = emailAddresses.Count > 0 ? emailAddresses[0] : null;
                                result.Elem("email", email);
                                _log.DebugFormat("E-mail address from AX: {0}", email);
                            }
                        }
                    }
                    response.Return(DreamMessage.Ok(result));
                    break;

                case AuthenticationStatus.Canceled:
                    _log.InfoFormat("Authentication was cancelled by the user.");
                    throw new DreamBadRequestException("Authentication was cancelled by the user.");

                case AuthenticationStatus.Failed:
                    _log.InfoFormat("Authentication failed: " + openIdResponse.Exception.Message);
                    throw new DreamBadRequestException("Authentication failed: " + openIdResponse.Exception.Message);

                default:
                    _log.WarnFormat("Authentication error: " + openIdResponse.Exception.Message);
                    throw new DreamBadRequestException("Authentication error: " + openIdResponse.Exception.Message);
                }
            }
            else
            {
                _log.Warn("OpenID response was null");
                throw new DreamBadRequestException("No OpenID response was returned.");
            }
            yield break;
        }
Esempio n. 49
0
        private void ConvertUsers(string htpasswdFilePath)
        {
            WriteLineToConsole("Converting users...");
            string[] userLines = File.ReadAllLines(htpasswdFilePath);

            Dictionary<string, string> dekiUsers = new Dictionary<string, string>();

            DreamMessage usersResponse = _dekiPlug.At("users").With("limit", int.MaxValue).GetAsync().Wait();

            if (usersResponse.Status != DreamStatus.Ok)
            {
                WriteErrorResponse(usersResponse, "Error while reciving users from Deki. Users not converted.");
                return;
            }

            XDoc dekiUsersDoc = usersResponse.AsDocument();
            foreach (XDoc userDoc in dekiUsersDoc["//user"])
            {
                string dekiUserName = userDoc["nick"].AsText;
                dekiUsers[dekiUserName.ToLower()] = null;
            }

            foreach (string userLine in userLines)
            {
                string user = userLine.Trim();
                if (string.IsNullOrEmpty(user))
                {
                    continue;
                }
                int colonIndex = user.IndexOf(':');
                if (colonIndex <= 0)
                {
                    continue;
                }
                string userName = user.Substring(0, colonIndex);
                if (_convertedUsers.ContainsKey(userName))
                {
                    continue;
                }
                string eMail = null;
                int lastColonIndex = user.LastIndexOf(':');
                if ((lastColonIndex > 0) && (lastColonIndex > colonIndex) && (lastColonIndex + 1 < user.Length))
                {
                    eMail = user.Substring(lastColonIndex + 1, user.Length - lastColonIndex - 1);
                }

                string newUserName = userName;
                int userNum = 0;
                while (dekiUsers.ContainsKey(newUserName.ToLower()))
                {
                    userNum++;
                    newUserName = userName + userNum.ToString();
                }

                if (newUserName != userName)
                {
                    WriteLineToConsole("TWiki user \"" + userName + "\" converted as \"" + newUserName + "\" becouse of existing same user in Deki");
                }

                XDoc usersDoc = new XDoc("user")
                    .Elem("username", newUserName);
                if (!string.IsNullOrEmpty(eMail))
                {
                    usersDoc.Elem("email", eMail);
                }

                string newPassword = Guid.NewGuid().ToString();

                DreamMessage res = _dekiPlug.At("users").With("accountpassword", newPassword).PostAsync(usersDoc).Wait();
                WriteErrorResponse(res, "Error converting user \"" + userName + "\"");

                XDoc resDoc = res.AsDocument();
                int dekiId = resDoc["@id"].AsInt.Value;

                _convertedUsers[userName] = new TWikiUser(userName, newUserName, dekiId);
            }

            WriteLineToConsole("Users converted!!!");
            WriteLineToConsole();
        }
Esempio n. 50
0
        public virtual Yield GetServiceInfo(DreamContext context, DreamMessage request, Result <DreamMessage> response)
        {
            XDoc   blueprint = Blueprint;
            string title     = blueprint["name"].AsText ?? "Service Blueprint";
            XDoc   result    = new XDoc("html").Attr("xmlns", "http://www.w3.org/1999/xhtml")
                               .Start("head")
                               .Elem("title", title)
                               .Start("meta").Attr("http-equiv", "content-type").Attr("content", "text/html;charset=utf-8").End()
                               .Start("meta").Attr("http-equiv", "Content-Style-Type").Attr("content", "text/css").End()
                               .End();

            if (blueprint.IsEmpty)
            {
                result.Elem("body", "Missing service blueprint");
            }
            else
            {
                result.Start("body")
                .Elem("h1", title)
                .Start("p")
                .Value(blueprint["copyright"].Contents)
                .Value(" ")
                .Start("a").Attr("href", blueprint["info"].Contents).Value("(more)").End()
                .Value(" ")
                .Start("a").Attr("href", Self.Uri.At("@blueprint").Path).Value("(blueprint)").End()
                .End();

                // show configuration information
                XDoc config = blueprint["configuration"];
                if (!config.IsEmpty)
                {
                    result.Elem("h2", "Configuration");
                    result.Start("ul");
                    foreach (XDoc entry in config["entry"])
                    {
                        result.Start("li");
                        if (entry["valuetype"].Contents != string.Empty)
                        {
                            result.Value(string.Format("{0} = {1} : {2}", entry["name"].Contents, entry["valuetype"].Contents, entry["description"].Contents));
                        }
                        else
                        {
                            result.Value(string.Format("{0} : {1}", entry["name"].Contents, entry["description"].Contents));
                        }
                        result.End();
                    }
                    result.End();
                }

                // sort features by signature then verb
                blueprint["features"].Sort(delegate(XDoc first, XDoc second) {
                    string[] firstPattern  = first["pattern"].Contents.Split(new[] { ':' }, 2);
                    string[] secondPattern = second["pattern"].Contents.Split(new[] { ':' }, 2);
                    int cmp = firstPattern[1].CompareInvariantIgnoreCase(secondPattern[1]);
                    if (cmp != 0)
                    {
                        return(cmp);
                    }
                    return(firstPattern[0].CompareInvariant(secondPattern[0]));
                });

                // display features
                XDoc features = blueprint["features/feature"];
                if (!features.IsEmpty)
                {
                    result.Elem("h2", "Features");
                    List <string> modifiers = new List <string>();
                    foreach (XDoc feature in features)
                    {
                        modifiers.Clear();

                        // add modifiers
                        string modifier = feature["access"].AsText;
                        if (modifier != null)
                        {
                            modifiers.Add(modifier);
                        }
                        modifier = feature["obsolete"].AsText;
                        if (modifier != null)
                        {
                            modifiers.Add("OBSOLETE => " + modifier);
                        }
                        if (modifiers.Count > 0)
                        {
                            modifier = " (" + string.Join(", ", modifiers.ToArray()) + ")";
                        }
                        else
                        {
                            modifier = string.Empty;
                        }

                        // check if feature has GET verb and no path parameters
                        string pattern = feature["pattern"].Contents;
                        if (pattern.StartsWithInvariantIgnoreCase(Verb.GET + ":") && (pattern.IndexOfAny(new[] { '{', '*', '?' }) == -1))
                        {
                            string[] parts = pattern.Split(new[] { ':' }, 2);
                            result.Start("h3")
                            .Start("a").Attr("href", context.AsPublicUri(Self.Uri.AtPath(parts[1])))
                            .Value(feature["pattern"].Contents)
                            .End()
                            .Value(modifier)
                            .End();
                        }
                        else
                        {
                            result.Elem("h3", feature["pattern"].Contents + modifier);
                        }
                        result.Start("p")
                        .Value(feature["description"].Contents)
                        .Value(" ")
                        .Start("a").Attr("href", feature["info"].Contents).Value("(more)").End();
                        XDoc paramlist = feature["param"];
                        if (!paramlist.IsEmpty)
                        {
                            result.Start("ul");
                            foreach (XDoc param in paramlist)
                            {
                                result.Start("li");
                                if (param["valuetype"].Contents != string.Empty)
                                {
                                    result.Value(string.Format("{0} = {1} : {2}", param["name"].Contents, param["valuetype"].Contents, param["description"].Contents));
                                }
                                else
                                {
                                    result.Value(string.Format("{0} : {1}", param["name"].Contents, param["description"].Contents));
                                }
                                result.End();
                            }
                            result.End();
                        }
                        result.End();
                    }
                }
            }
            response.Return(DreamMessage.Ok(MimeType.HTML, result.ToString()));
            yield break;
        }
Esempio n. 51
0
        public Yield GetNavigationChildren(DreamContext context, DreamMessage request, Result<DreamMessage> response) {
            CheckResponseCache(context, false);

            PageBE page = PageBL_GetPageFromUrl(context, false);
            if (page.Title.IsTalk) {
                page = PageBL.GetPageByTitle(page.Title.AsFront());
            }

            // build response
            uint exclude = context.GetParam<uint>("exclude", 0);
            IList<NavBE> list = NavBL.QueryNavChildrenData(page, context.Culture);
            if(ShowDebug(context)) {
                response.Return(DreamMessage.Ok(NavBL.ConvertNavPageListToDoc(list)));
            } else {
                bool expandableNav = context.GetParam("type", "compact").EqualsInvariantIgnoreCase("expandable");
                XDoc doc = expandableNav ? NavBL.ComputeExpandableNavigationDocument(list, page, 0, exclude, true) : NavBL.ComputeNavigationDocument(list, page, 0, exclude, true, context.GetParam("width", int.MaxValue));
                if(ShowXml(context)) {
                    response.Return(DreamMessage.Ok(doc));
                } else {
                    XDoc result = new XDoc("tree");
                    result.Start("children");

                    // add name of children nodes
                    System.Text.StringBuilder nodes = new System.Text.StringBuilder();
                    ulong homepageId = DekiContext.Current.Instance.HomePageId;
                    ulong parentId = (page.ID == homepageId) ? 0 : page.ID;
                    foreach(NavBE child in list) {
                        if((child.ParentId == parentId) && (child.Id != homepageId)) {
                            if(nodes.Length != 0) {
                                nodes.Append(",");
                            }
                            nodes.AppendFormat("n{0}", child.Id);
                        }
                    }
                    result.Elem("nodes", nodes.ToString());

                    // add <div> list
                    result.Start("html");
                    if(exclude != 0) {
                        result.Start("pre").Value(doc["children-pre"].Contents).End();
                        result.Start("post").Value(doc["children-post"].Contents).End();
                    } else {
                        result.Value(doc.Contents);
                    }
                    result.End();
                    result.End();
                    response.Return(DreamMessage.Ok(result));
                }
            }
            yield break;
        }
Esempio n. 52
0
        //--- Class Methods ---

        /// <summary>
        /// Create a service blueprint from reflection and attribute meta-data for an <see cref="IDreamService"/> implementation.
        /// </summary>
        /// <param name="type">Type of examine.</param>
        /// <returns>Xml formatted blueprint.</returns>
        public static XDoc CreateServiceBlueprint(Type type)
        {
            if (type == null)
            {
                throw new ArgumentNullException("type");
            }
            XDoc result = new XDoc("blueprint");

            // load assembly
            Dictionary <string, string> assemblySettings = new Dictionary <string, string>(StringComparer.Ordinal);

            string[] assemblyParts = type.Assembly.FullName.Split(',');
            foreach (string parts in assemblyParts)
            {
                string[] assign = parts.Trim().Split(new char[] { '=' }, 2);
                if (assign.Length == 2)
                {
                    assemblySettings[assign[0].Trim()] = assign[1].Trim();
                }
            }
            result.Start("assembly");
            foreach (KeyValuePair <string, string> entry in assemblySettings)
            {
                result.Attr(entry.Key, entry.Value);
            }
            result.Value(assemblyParts[0]);
            result.End();
            result.Elem("class", type.FullName);

            // retrieve DreamService attribute on class definition
            DreamServiceAttribute serviceAttrib = (DreamServiceAttribute)Attribute.GetCustomAttribute(type, typeof(DreamServiceAttribute), false);

            result.Elem("name", serviceAttrib.Name);
            result.Elem("copyright", serviceAttrib.Copyright);
            result.Elem("info", serviceAttrib.Info);

            // retrieve DreamServiceUID attributes
            foreach (XUri sid in serviceAttrib.GetSIDAsUris())
            {
                result.Elem("sid", sid);
            }

            // check if service has blueprint settings
            foreach (DreamServiceBlueprintAttribute blueprintAttrib in Attribute.GetCustomAttributes(type, typeof(DreamServiceBlueprintAttribute), true))
            {
                result.InsertValueAt(blueprintAttrib.Name, blueprintAttrib.Value);
            }

            // check if service has configuration information
            DreamServiceConfigAttribute[] configAttributes = (DreamServiceConfigAttribute[])Attribute.GetCustomAttributes(type, typeof(DreamServiceConfigAttribute), true);
            if (!ArrayUtil.IsNullOrEmpty(configAttributes))
            {
                result.Start("configuration");
                foreach (DreamServiceConfigAttribute configAttr in configAttributes)
                {
                    result.Start("entry")
                    .Elem("name", configAttr.Name)
                    .Elem("valuetype", configAttr.ValueType)
                    .Elem("description", configAttr.Description)
                    .End();
                }
                result.End();
            }

            // retrieve DreamFeature attributes on method definitions
            result.Start("features");
            MethodInfo[] methods = type.GetMethods(BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic);
            foreach (MethodInfo method in methods)
            {
                // retrieve feature description
                Attribute[] featureAttributes = Attribute.GetCustomAttributes(method, typeof(DreamFeatureAttribute), false);
                if (featureAttributes.Length == 0)
                {
                    continue;
                }
                if (method.IsGenericMethod || method.IsGenericMethodDefinition)
                {
                    throw new NotSupportedException(string.Format("generic methods are not supported ({0})", method.Name));
                }

                // determine access level
                string access;
                if (method.IsPublic)
                {
                    access = "public";
                }
                else if (method.IsAssembly)
                {
                    access = "internal";
                }
                else if (method.IsPrivate || method.IsFamily)
                {
                    access = "private";
                }
                else
                {
                    throw new NotSupportedException(string.Format("access level is not supported ({0})", method.Name));
                }

                // retrieve feature parameter descriptions, filters, prologues, and epilogues
                Attribute[] paramAttributes = Attribute.GetCustomAttributes(method, typeof(DreamFeatureParamAttribute), false);
                var         pathAttributes  = method.GetParameters().Select(p => {
                    var attr = (PathAttribute)p.GetCustomAttributes(typeof(PathAttribute), false).FirstOrDefault();
                    return(((attr != null) && (attr.Name == null)) ? new PathAttribute {
                        Description = attr.Description, Name = p.Name
                    } : attr);
                }).Where(p => p != null);
                var queryAttributes = method.GetParameters().Select(q => {
                    var attr = (QueryAttribute)q.GetCustomAttributes(typeof(QueryAttribute), false).FirstOrDefault();
                    return(((attr != null) && (attr.Name == null)) ? new QueryAttribute {
                        Description = attr.Description, Name = q.Name
                    } : attr);
                }).Where(q => q != null);
                Attribute[] statusAttributes = Attribute.GetCustomAttributes(method, typeof(DreamFeatureStatusAttribute), false);
                foreach (DreamFeatureAttribute featureAttrib in featureAttributes)
                {
                    result.Start("feature");
                    result.Elem("obsolete", featureAttrib.Obsolete);
                    result.Elem("pattern", featureAttrib.Pattern);
                    result.Elem("description", featureAttrib.Description);
                    string info = featureAttrib.Info ?? serviceAttrib.Info;
                    if (info != null)
                    {
                        result.Elem("info", info);
                    }
                    result.Elem("method", method.Name);

                    // add parameter descriptions (as seen on the method definition)
                    foreach (DreamFeatureParamAttribute paramAttrib in paramAttributes)
                    {
                        result.Start("param");
                        result.Elem("name", paramAttrib.Name);
                        if (!string.IsNullOrEmpty(paramAttrib.ValueType))
                        {
                            result.Elem("valuetype", paramAttrib.ValueType);
                        }
                        result.Elem("description", paramAttrib.Description);
                        result.End();
                    }

                    // add parameter descriptions (as seen on the method parameters)
                    foreach (PathAttribute pathAttrib in pathAttributes)
                    {
                        result.Start("param")
                        .Elem("name", "{" + pathAttrib.Name + "}")
                        .Elem("description", pathAttrib.Description)
                        .End();
                    }

                    // add parameter descriptions (as seen on the method parameters)
                    foreach (QueryAttribute queryAttrib in queryAttributes)
                    {
                        result.Start("param")
                        .Elem("name", queryAttrib.Name)
                        .Elem("description", queryAttrib.Description)
                        .End();
                    }

                    // add status codes
                    foreach (DreamFeatureStatusAttribute paramAttrib in statusAttributes)
                    {
                        result.Start("status");
                        result.Attr("value", (int)paramAttrib.Status);
                        result.Value(paramAttrib.Description);
                        result.End();
                    }

                    // add access level
                    result.Elem("access", access);
                    result.End();
                }
            }
            result.End();
            return(result.EndAll());
        }
Esempio n. 53
0
        private void CreateStorageService()
        {
            // create storage service
            XDoc config = new XDoc("config");
            config.Elem("path", "storage");
            config.Elem("sid", "sid://mindtouch.com/2007/03/dream/storage");
            config.Elem("folder", _storageFolder);
            //DreamMessage result = _host.Self.At("services").PostAsync(config).Wait();
            DreamMessage result = _hostInfo.LocalHost.At("host", "services").With("apikey", _hostInfo.ApiKey).PostAsync(config).Wait();
            Assert.IsTrue(result.IsSuccessful, result.ToText());

            // initialize storage plug
            _storage = _hostInfo.LocalHost.At("storage");
        }
Esempio n. 54
0
 private static XDoc GetDefaultErrorResponse(DreamStatus status, string title, string message) {
     XDoc result = new XDoc("error");
     DreamContext context = DreamContext.CurrentOrNull;
     if((context != null) && (context.Env.Self != null)) {
         result.WithXslTransform(context.AsPublicUri(context.Env.Self).At("resources", "error.xslt").Path);
     }
     result.Elem("status", (int)status).Elem("title", title).Elem("message", message);
     if(context != null) {
         result.Elem("uri", context.Uri);
     }
     return result;
 }
Esempio n. 55
0
        private XDoc BuildBugListHTMLTable(XmlRpcStruct[] bugs, int[] ticketIds) {
            XDoc ret = new XDoc("div").Attr("class", "DW-table Trac-table table");
            ret.Start("table").Attr("border", 0).Attr("cellspacing", 0).Attr("cellpadding", 0).Attr("class", "table feedtable sortable");

            // header
            ret.Start("tr")
                .Elem("th", "Bug#")
                .Elem("th", "Summary")
                .Elem("th", "Status")
                .Elem("th", "Severity")
                .Elem("th", "Opened By")
                .Elem("th", "Assigned To")

            .End();

            for(int i=0; i < bugs.Length; i++){
                XmlRpcStruct bug = bugs[i];
                string status = bug["status"].ToString();
                string reporter = bug["reporter"].ToString();

                // The severity-param is not submitted by trac if no severity-entry is defined
                string severity = string.Empty;
                if(bug["severity"] != null) {
                    severity = bug["severity"].ToString();
                }
                string owner = bug["owner"].ToString();
                string summary = bug["summary"].ToString();

                string trClass = string.Format("{0} {1}", (i % 2 == 0) ? "even" : "odd", status);
                ret.Start("tr").Attr("class", trClass);
                ret.Start("td");
                ret = BuildBugLink(bug, ret, ticketIds[i]);
                ret.End(); //td;
                ret.Elem("td", summary);
                ret.Start("td").Value(status).End();
                ret.Start("td").Value(severity).End();
                ret.Elem("td", reporter);
                ret.Elem("td", owner);

                ret.End();//tr
            }
            ret.End(); // table
            return ret;
        }
Esempio n. 56
0
        public XDoc Table(
            [DekiExtParam("SELECT query")] string query
        ) {
            XDoc result = new XDoc("html")
                .Start("head")
                    .Start("script").Attr("type", "text/javascript").Attr("src", Files.At("sorttable.js")).End()
                    .Start("style").Attr("type", "text/css").Value(@".feedtable {
    border:1px solid #999;
    line-height:1.5em;
    overflow:hidden;
    width:100%;
}
.feedtable th {
    background-color:#ddd;
    border-bottom:1px solid #999;
    font-size:14px;
}
.feedtable tr {
    background-color:#FFFFFF;
}
.feedtable tr.feedroweven td {
    background-color:#ededed;
}").End()
                .End()
                .Start("body");
            result.Start("table").Attr("border", 0).Attr("cellpadding", 0).Attr("cellspacing", 0).Attr("class", "feedtable sortable");
            _catalog.NewQuery(query).Execute(delegate(IDataReader reader) {

                // capture row columns
                result.Start("thead").Start("tr");
                int count = reader.FieldCount;
                for(int i = 0; i < count; ++i) {
                    result.Start("th").Elem("strong", reader.GetName(i)).End();
                }
                result.End().End();

                // read records
                int rowcount = 0;
                result.Start("tbody");
                while(reader.Read()) {
                    result.Start("tr");
                    result.Attr("class", ((rowcount++ & 1) == 0) ? "feedroweven" : "feedrowodd");
                    for (int i = 0; i < count; ++i) {
                        string val = string.Empty;

                        try {
                            if (!reader.IsDBNull(i)) {
                                val = reader.GetValue(i).ToString();
                            }
                        } catch { }
                     
                        result.Elem("td", val);
                    }
                    result.End();
                }
                result.End();
            });
            result.End().End();
            return result;
        }
Esempio n. 57
0
        public Yield GetFileOrFolderListing(DreamContext context, DreamMessage request, Result <DreamMessage> response)
        {
            bool   head = StringUtil.EqualsInvariant(context.Verb, "HEAD");
            string path = GetPath(context);

            DreamMessage result;

            if (File.Exists(path))
            {
                // dealing with a file request
                TouchMeta(path);

                // check if request contains a 'if-modified-since' header
                var lastmodified = File.GetLastWriteTime(path);
                if (request.CheckCacheRevalidation(lastmodified) && (lastmodified.Year >= 1900))
                {
                    response.Return(DreamMessage.NotModified());
                    yield break;
                }

                // retrieve file
                try {
                    result = DreamMessage.FromFile(path, head);
                } catch (FileNotFoundException) {
                    result = DreamMessage.NotFound("file not found");
                } catch (Exception) {
                    result = DreamMessage.BadRequest("invalid path");
                }

                // add caching headers if file was found
                if (!head && result.IsSuccessful)
                {
                    // add caching information; this will avoid unnecessary data transfers by user-agents with caches
                    result.SetCacheMustRevalidate(lastmodified);
                }
            }
            else if (Directory.Exists(path))
            {
                // dealing with a directory request
                if (head)
                {
                    // HEAD for a directory doesn't really mean anything, so we just return ok, to indicate that it exists
                    result = DreamMessage.Ok();
                }
                else
                {
                    var doc = new XDoc("files");

                    // list directory contents
                    var directories = Directory.GetDirectories(path);
                    foreach (var dir in directories)
                    {
                        if (dir.EndsWithInvariantIgnoreCase(META))
                        {
                            continue;
                        }
                        doc.Start("folder")
                        .Elem("name", Path.GetFileName(dir))
                        .End();
                    }
                    foreach (var filepath in Directory.GetFiles(path))
                    {
                        var file = new FileInfo(filepath);
                        doc.Start("file")
                        .Elem("name", file.Name)
                        .Elem("size", file.Length)
                        .Elem("date.created", file.CreationTimeUtc)
                        .Elem("date.modified", file.LastWriteTimeUtc);
                        var entry = SyncMeta(filepath);
                        if (entry != null)
                        {
                            doc.Elem("date.expire", entry.When);
                            doc.Elem("date.ttl", entry.TTL);
                        }
                        doc.End();
                    }
                    result = DreamMessage.Ok(doc);
                }
            }
            else
            {
                // nothin here
                result = DreamMessage.NotFound("no such file or folder");
            }

            response.Return(result);
            yield break;
        }
Esempio n. 58
0
        public XDoc Table(
            [DekiExtParam("SELECT query")] string query
            )
        {
            XDoc result = new XDoc("html")
                          .Start("head")
                          .Start("script").Attr("type", "text/javascript").Attr("src", Files.At("sorttable.js")).End()
                          .Start("style").Attr("type", "text/css").Value(@".feedtable {
    border:1px solid #999;
    line-height:1.5em;
    overflow:hidden;
    width:100%;
}
.feedtable th {
    background-color:#ddd;
    border-bottom:1px solid #999;
    font-size:14px;
}
.feedtable tr {
    background-color:#FFFFFF;
}
.feedtable tr.feedroweven td {
    background-color:#ededed;
}").End()
                          .End()
                          .Start("body");

            result.Start("table").Attr("border", 0).Attr("cellpadding", 0).Attr("cellspacing", 0).Attr("class", "feedtable sortable");
            _catalog.NewQuery(query).Execute(delegate(IDataReader reader) {
                // capture row columns
                result.Start("thead").Start("tr");
                int count = reader.FieldCount;
                for (int i = 0; i < count; ++i)
                {
                    result.Start("th").Elem("strong", reader.GetName(i)).End();
                }
                result.End().End();

                // read records
                int rowcount = 0;
                result.Start("tbody");
                while (reader.Read())
                {
                    result.Start("tr");
                    result.Attr("class", ((rowcount++ & 1) == 0) ? "feedroweven" : "feedrowodd");
                    for (int i = 0; i < count; ++i)
                    {
                        string val = string.Empty;

                        try {
                            if (!reader.IsDBNull(i))
                            {
                                val = reader.GetValue(i).ToString();
                            }
                        } catch { }

                        result.Elem("td", val);
                    }
                    result.End();
                }
                result.End();
            });
            result.End().End();
            return(result);
        }
Esempio n. 59
0
        private void AppendDiff(bool diffCacheEnabled, XDoc body, RecentChangeEntry change, RC type, Title title, IDictionary<string, XDoc> cache) {
            var resources = DekiContext.Current.Resources;
            ulong pageid = change.CurId;
            int? after = (change.Revision > 0) ? (int?)change.Revision : null;
            int? before = change.PreviousRevision;

            // append edit summary, if any
            body.Elem("p", change.Summary);

            // append comment(s)
            int count = (change.ExtraComments == null) ? (string.IsNullOrEmpty(change.Comment) ? 0 : 1) : change.ExtraComments.Count;
            switch(count) {
            case 0:

                // nothing to do
                break;
            case 1:
                body.Elem("p", (change.ExtraComments != null) ? change.ExtraComments[0].Item3 : change.Comment);
                break;
            default:
                body.Start("ol");
                foreach(var comment in ((IEnumerable<Tuplet<string, string, string>>)change.ExtraComments).Reverse()) {
                    string author = string.IsNullOrEmpty(comment.Item2) ? comment.Item1 : comment.Item2;
                    body.Elem("li", string.IsNullOrEmpty(author) ? comment.Item3 : string.Format("{0} ({1})", comment.Item3, author));
                }
                body.End();
                break;
            }

            // check if page was modified
            if(after.HasValue && before.HasValue && (after != before)) {

                // check if we have a cached version of this page diff
                XDoc diffXml = null;
                Plug store = Storage.At("site_" + XUri.EncodeSegment(DekiContext.Current.Instance.Id), DreamContext.Current.Culture.Name, "feeds", string.Format("page_{0}", pageid), string.Format("diff_{0}-{1}.xml", before, after));
                if(diffCacheEnabled) {
                    var v = store.Get(new Result<DreamMessage>(TimeSpan.MaxValue)).Wait();
                    diffXml = (v.IsSuccessful && v.HasDocument) ? v.ToDocument() : null;

                    if(diffXml != null) {

                        // TODO (steveb): this problem only exists b/c we can't determine the actual revision number that we should use for diffing (see bug 7824)

                        // check if either revision has been hidden since we computed the diff
                        var session = DbUtils.CurrentSession;
                        if(after.Value != change.CurrentRevision) {
                            OldBE afterRevision = session.Old_GetOldByRevision(pageid, (ulong)after.Value);
                            if((afterRevision == null) || afterRevision.IsHidden) {
                                diffXml = null;
                            }
                        }
                        if((diffXml != null) && (before.Value != change.CurrentRevision) && (before.Value > 0)) {
                            OldBE beforeRevision = session.Old_GetOldByRevision(pageid, (ulong)before.Value);
                            if((beforeRevision == null) || beforeRevision.IsHidden) {
                                diffXml = null;
                            }
                        }
                    }
                }
                if(diffXml == null) {
                    diffXml = new XDoc("diff");

                    // retrieve page versions
                    XDoc res = QueryPageVersions(pageid, after, before, cache);
                    XDoc beforeDoc = res["before/body"];
                    XDoc afterDoc = res["after/body"];

                    // check if either both versions or only one version were retrieved
                    XDoc diff = XDoc.Empty;
                    XDoc invisibleDiff = XDoc.Empty;
                    string summary = null;
                    if(!beforeDoc.IsEmpty && !afterDoc.IsEmpty) {
                        XDoc beforeChanges;
                        XDoc afterChanges;
                        DekiResource summaryResource = null;

                        // compute differences between 'before' and 'after' versions
                        diff = Utils.GetPageDiff(beforeDoc, afterDoc, true, DekiContext.Current.Instance.MaxDiffSize, out invisibleDiff, out summaryResource, out beforeChanges, out afterChanges);

                        // TODO (arnec): why are we using ToLower here at all and without a culture?
                        summary = resources.Localize(summaryResource).ToLower();
                    } else if(!afterDoc.IsEmpty) {

                        // since we don't have a 'before' version, just show the entire 'after' version (can happen for new pages or hidden revisions)
                        diff = afterDoc;
                    } else if(!beforeDoc.IsEmpty) {

                        // since we don't have a 'after' version, just show the entire 'before' version (can happen for hidden revisions)
                        diff = beforeDoc;
                    }

                    // add change summary
                    diffXml.Start("blockquote");
                    diffXml.Start("p").Elem("strong", summary).End();

                    // check if a diff was computed
                    if(!diff.IsEmpty) {
                        diffXml.Start("hr").Attr("width", "100%").Attr("size", "2").End();
                        diffXml.AddNodes(diff);
                        diffXml.Start("hr").Attr("width", "100%").Attr("size", "2").End();

                        // check if there are invisible changes as well to show
                        if(!invisibleDiff.IsEmpty) {
                            diffXml.Start("p").Elem("strong", resources.Localize(DekiResources.PAGE_DIFF_OTHER_CHANGES())).End();
                            diffXml.Add(invisibleDiff);
                        }
                    } else if(!invisibleDiff.IsEmpty) {

                        // only show invisible changes
                        diffXml.Start("hr").Attr("width", "100%").Attr("size", "2").End();
                        diffXml.Start("p").Elem("strong", resources.Localize(DekiResources.PAGE_DIFF_OTHER_CHANGES())).End();
                        diffXml.Add(invisibleDiff);
                    } else if(beforeDoc.IsEmpty && afterDoc.IsEmpty) {

                        // show message that page contents were not available anymore
                        diffXml.Elem("p", resources.Localize(DekiResources.PAGE_NOT_AVAILABLE()));
                    }
                    diffXml.End();

                    // store diff in cache
                    if(diffCacheEnabled && !afterDoc.IsEmpty) {
                        store.With("ttl", TimeSpan.FromDays(30).TotalSeconds).Put(diffXml, new Result<DreamMessage>(TimeSpan.MaxValue)).Block();
                    }
                }
                body.AddNodes(diffXml);
            }

            // check if we have a comment text
            if(Utils.IsPageComment(type)) {
                string text = change.CmntContent;
                if(!string.IsNullOrEmpty(text) && !change.CmntDeleted) {
                    MimeType mime = new MimeType(change.CmntMimetype ?? MimeType.TEXT_UTF8.ToString());
                    if(mime.Match(MimeType.HTML)) {
                        XDoc html = XDocFactory.From(string.Format("<html><body>{0}</body></html>", text), MimeType.HTML);
                        body.Start("blockquote").AddNodes(html["body"]).End();
                    } else {

                        // anything else should be consider to be text
                        body.Start("blockquote").Elem("p", text).End();
                    }
                } else {

                    // anything else should be consider to be text
                    body.Start("blockquote").Elem("p", resources.Localize(DekiResources.COMMENT_NOT_AVAILABLE())).End();
                }
            }

            // adds links
            body.Start("table").Attr("border", 0).Attr("padding", "5").Attr("width", "80%").Start("tr");

            // add link for viewing the page
            if(change.PageExists) {
                Title view = new Title(title);
                body.Start("td").Start("a").Attr("href", Utils.AsPublicUiUri(view, true)).Value(resources.Localize(DekiResources.VIEW_PAGE())).End().End();
            }

            // check if we need to add link for editing the page
            if(after.HasValue && before.HasValue && (after != before)) {
                Title edit = new Title(title) { Query = "action=edit" };
                body.Start("td").Start("a").Attr("href", Utils.AsPublicUiUri(edit)).Value(resources.Localize(DekiResources.EDIT_PAGE())).End().End();
            }

            // check if we need to add link for viewing the complete diff
            if(after.HasValue && before.HasValue && (after != before)) {
                Title show = new Title(title) { Query = string.Format("diff={0}&revision={1}", after.Value, before.Value) };
                body.Start("td").Start("a").Attr("href", Utils.AsPublicUiUri(show, true)).Value(resources.Localize(DekiResources.VIEW_PAGE_DIFF())).End().End();
            }

            // check if we need to add link for seeing full page history
            if(after.HasValue && before.HasValue && (after != before)) {
                Title history = new Title(title) { Query = "action=history" };
                body.Start("td").Start("a").Attr("href", Utils.AsPublicUiUri(history)).Value(resources.Localize(DekiResources.VIEW_PAGE_HISTORY())).End().End();
            }

            // check if we need to add link for banning the user
            List<KeyValuePair<string, string>> authors = change.SortedAuthors;
            if((authors == null) || (authors.Count == 0)) {
                authors = new List<KeyValuePair<string, string>> { new KeyValuePair<string, string>(change.Username, change.Fullname) };
            }
            for(int i = 0; i < authors.Count; ++i) {
                string username = authors[i].Key;
                string fullname = authors[i].Value;
                if(!string.IsNullOrEmpty(username)) {

                    // don't put up ban link for admins.
                    UserBE user = DbUtils.CurrentSession.Users_GetByName(username);
                    if(!UserBL.IsAnonymous(user) && !PermissionsBL.IsUserAllowed(user, Permissions.ADMIN)) {
                        Title ban = Title.FromUIUri(null, "Special:Userban");
                        ban.Query += string.Format("username={0}", username);
                        body.Start("td").Start("a").Attr("href", Utils.AsPublicUiUri(ban)).Value(resources.Localize(DekiResources.BAN_USER(string.IsNullOrEmpty(fullname) ? username : fullname))).End().End();
                    }
                }
            }

            // close HTML
            body.End().End();
        }
Esempio n. 60
0
        private void MoveGroups()
        {
            DreamMessage msg = _dekiPlug.At("groups").With("limit", int.MaxValue).GetAsync().Wait();

            if (msg.Status != DreamStatus.Ok)
            {
                WriteLineToConsole("Error while receiving groups from Deki. Groups not converted.");
                WriteErrorResponse(msg);
                return;
            }

            Dictionary <string, string> dekiGroups = new Dictionary <string, string>();

            XDoc groupsDoc = msg.AsDocument();

            foreach (XDoc groupDoc in groupsDoc["//group"])
            {
                string dekiGroupName = groupDoc["groupname"].AsText;
                dekiGroups[dekiGroupName.ToLower()] = null;
            }

            string[] confluenceGroupNames = _confluenceService.GetGroups();

            foreach (string confluenceGroupName in confluenceGroupNames)
            {
                string dekiGroupName;
                if (!_convertedGroups.ContainsKey(confluenceGroupName.ToLower()))
                {
                    int groupNum = 0;
                    dekiGroupName = confluenceGroupName;
                    while (dekiGroups.ContainsKey(dekiGroupName.ToLower()))
                    {
                        groupNum++;
                        dekiGroupName = confluenceGroupName + groupNum.ToString();
                    }
                    if (dekiGroupName != confluenceGroupName)
                    {
                        WriteLineToConsole("Confluence group \"" + confluenceGroupName + "\" converted as \"" + dekiGroupName + "\" becouse of existing same group in Deki");
                    }

                    XDoc newGroupDoc = new XDoc("group");
                    newGroupDoc.Elem("name", dekiGroupName)
                    .Start("users");

                    foreach (ACConverterUserInfo convertedUser in _convertedUsers.Values)
                    {
                        if (Array.IndexOf(convertedUser.ConfluenceUserGroupNames, confluenceGroupName) >= 0)
                        {
                            newGroupDoc.Start("user").Attr("id", convertedUser.DekiUserId).End();
                        }
                    }

                    newGroupDoc.End();

                    Log.DebugFormat("Creating group: {0}", dekiGroupName);

                    DreamMessage res = _dekiPlug.At("groups").PostAsync(newGroupDoc).Wait();
                    if (res.Status != DreamStatus.Ok)
                    {
                        WriteLineToLog("Error converting group \"" + confluenceGroupName + "\"");
                        WriteErrorResponse(res);
                        WriteErrorRequest(newGroupDoc);
                        continue;
                    }

                    XDoc resGroupsDoc   = res.AsDocument();
                    int  newDekiGroupId = resGroupsDoc["@id"].AsInt.Value;

                    ACConverterGroupInfo convertedGroup =
                        new ACConverterGroupInfo(confluenceGroupName, dekiGroupName, newDekiGroupId);
                    _convertedGroups[confluenceGroupName.ToLower()] = convertedGroup;
                }
                else
                {
                    //This group already converted during previous ACConverter start
                    dekiGroupName = _convertedGroups[confluenceGroupName.ToLower()].DekiGroupName;

                    XDoc usersDoc = new XDoc("users");
                    foreach (ACConverterUserInfo convertedUser in _convertedUsers.Values)
                    {
                        if (Array.IndexOf(convertedUser.ConfluenceUserGroupNames, confluenceGroupName) >= 0)
                        {
                            usersDoc.Start("user").Attr("id", convertedUser.DekiUserId).End();
                        }
                    }
                    DreamMessage res = _dekiPlug.At("groups", _convertedGroups[confluenceGroupName.ToLower()].DekiGroupId.ToString(),
                                                    "users").PutAsync(usersDoc).Wait();
                    if (res.Status != DreamStatus.Ok)
                    {
                        WriteLineToLog("Error converting group's users");
                        WriteErrorResponse(res);
                        WriteErrorRequest(usersDoc);
                    }
                }
            }
        }