在CKFinder v3中validation网站成员为用户

在开始这个问题之前,我应该指出我对ASP.NET和C#的了解非常少。

我正在尝试将ASP.NET版本的CKFinder v3集成到一个用不同语言构建的网站中,到目前为止一切顺利; 我有所有设置,因为我想要它,并且当我授予对CKF的无限制访问权限时它正在工作但我现在停留在试图通过仅validation我网站的某些成员来使用它来限制对它的访问。 CKFinder在我的网站上出现的所有页面只能由那些特定成员访问,但是如果有人知道我的“ckfinder.html”文件的直接路径,我需要更高级别的安全性。

在CKFinder的ASP版本中,我只是在检查我的成员权限的函数中添加了这一行,其中isEditor是一个布尔值,其值是根据我的数据库中的信息为每个成员分配的:

 session("accessckf")=isEditor 

然后编辑CKFinder的“config.asp”文件中的CheckAuthentication()函数来读取:

 function CheckAuthentication() CheckAuthentication=session("accessckf") end function 

阅读这篇“Howto” ,在v3中认证似乎要复杂得多 ,但经过大量的试验和错误以及Lesiman的一些帮助 ,我创建了这个C#文件,它位于我的CKF目录中:

           public void Configuration(IAppBuilder appBuilder){ var connectorBuilder=ConfigureConnector(); var connector=connectorBuilder.Build(new OwinConnectorFactory()); appBuilder.Map("/path/to/connector",builder=>builder.UseConnector(connector)); } public ConnectorBuilder ConfigureConnector(){ var connectorBuilder=new ConnectorBuilder(); connectorBuilder.SetAuthenticator(new MyAuthenticator()); return connectorBuilder; } public class MyAuthenticator:IAuthenticator{ public Task AuthenticateAsync(ICommandRequest commandRequest,CancellationToken cancellationToken){ var domain=HttpContext.Current.Request.Url.Host; var cookie=HttpContext.Current.Request.Cookies[urlDomain]; var password=""; var username=""; var user=new User(false,null); if (cookie!=null){ if (cookie["username"]!=null) username=cookie["username"]; if (cookie["password"]!=null) password=cookie["password"]; if(username!=""&&password!=""){ var connection=new OdbcConnection("database=[database];driver=MySQL;pwd=[pwd];server=[server];uid=[uid];"); connection.Open(); OdbcDataReader records=new OdbcCommand("SELECT ISEDITOR FROM MEMBERS WHERE USERNAME='"+username+"' AND PASSWORD='"+password+"'",connection).ExecuteReader(); if(records.HasRows){ records.Read(); bool isEditor=records.GetString(0)=="1"; var roles="member"; if(isEditor) roles="editor,member"; user=new User(isEditor,roles.Split(',')); } records.Close(); connection.Close(); } } return Task.FromResult((IUser)user); } }  

加载该页面不会产生任何错误(这并不一定意味着它正在工作,因为尝试从public class中向屏幕写入任何东西都不起作用,出于某种原因)所以现在我正处于以某种方式检查该文件的阶段认证。

最初,我曾尝试通过XMLHttp从我的函数中加载它来检查网站的会员权限,但是,正如我怀疑和Lesmian确认的那样,这是行不通的。 经过更多的试验和错误,我添加了代码来检查网站成员对C#文件的权限,这导致我到了现在的位置:卡住了!

我需要在CKFinder中编辑什么才能让它使用此自定义文件来检查用户是否经过身份validation?

首先,您需要ASP会话和CKFinder的.Net身份validation器之间的连接器。 这是一个将ASP Session内容序列化为JSON的示例。

connector.asp放入可公开访问的位置。 例如, http://myaspwebsite.com/connector.asp

connector.asp

 <%@Language=VBScript CodePage=65001%> <% Option Explicit %>  <% ' obtain JSON.asp from https://github.com/tugrul/aspjson/archive/master.zip ' just for testing, must be removed in the production environment Session("isEditor") = True Session("isMember") = True ' only local requests allowed ' instead of local and remote ip comparison, a secret key can be used If Request.ServerVariables("LOCAL_ADDR") <> Request.ServerVariables("REMOTE_ADDR") Then Response.Status = "403 Forbidden" Response.End End If Response.ContentType = "application/json" Response.Charset = "utf-8" Dim JSONObject, Key Set JSONObject = jsObject() For Each Key In Session.Contents If Not IsObject(Session.Contents(Key)) Then 'skip the objects cannot be serialized JSONObject(Key) = Session.Contents(Key) End If Next JSONObject.Flush %> 

CKFinder 3.3.0附带一个默认连接器,可以在/ckfinder/bin/CKSource.CKFinder.Connector.WebApp.dll找到, 将其删除

检查以下程序并记住替换builder.Map("/connector", SetupConnector);new Uri("http://myaspwebsite.com/connector.asp"); 用你自己的价值观。

它只是通过检查ASP Session变量isEditorisMember via connector.asp来validation用户,最后声明角色editormember或无。

我假设您已在web.config配置了角色editormember

然后将Shaggy.cs放入/ckfinder/App_Code 。 如果不存在,则创建App_Code目录。 此文件夹中的.Net文件将即时编译。

有关更多信息,请查看ASP.NET Web项目中的共享代码文件夹

Shaggy.cs

 using System; using System.Collections.Generic; using System.Linq; using System.Net; using System.Threading; using System.Threading.Tasks; using Microsoft.Owin.Security; using Microsoft.Owin.Security.Cookies; using Newtonsoft.Json.Linq; using Owin; [assembly: Microsoft.Owin.OwinStartup(typeof(CKSource.CKFinder.Connector.Shaggy.Startup))] namespace CKSource.CKFinder.Connector.Shaggy { using FileSystem.Local; using FileSystem.Dropbox; using Core; using Core.Authentication; using Config; using Core.Builders; using Core.Logs; using Host.Owin; using Logs.NLog; using KeyValue.EntityFramework; public class Startup { public void Configuration(IAppBuilder builder) { LoggerManager.LoggerAdapterFactory = new NLogLoggerAdapterFactory(); RegisterFileSystems(); builder.UseCookieAuthentication(new CookieAuthenticationOptions { AuthenticationType = "ApplicationCookie", AuthenticationMode = AuthenticationMode.Active }); //replace connector path with yours builder.Map("/connector", SetupConnector); } private static void RegisterFileSystems() { FileSystemFactory.RegisterFileSystem(); FileSystemFactory.RegisterFileSystem(); } private static void SetupConnector(IAppBuilder builder) { var keyValueStoreProvider = new EntityFrameworkKeyValueStoreProvider("CacheConnectionString"); var authenticator = new ShaggysAuthenticator(); var connectorFactory = new OwinConnectorFactory(); var connectorBuilder = new ConnectorBuilder(); var connector = connectorBuilder .LoadConfig() .SetAuthenticator(authenticator) .SetRequestConfiguration( (request, config) => { config.LoadConfig(); config.SetKeyValueStoreProvider(keyValueStoreProvider); }) .Build(connectorFactory); builder.UseConnector(connector); } } public class ShaggysAuthenticator : IAuthenticator { // this method makes an http request on the background to gather ASP's all session contents and returns a JSON object // if the request contains ASP's session cookie(s) private static JObject GetAspSessionState(ICommandRequest requestContext) { // building Cookie header with ASP's session cookies var aspSessionCookies = string.Join(";", requestContext.Cookies.Where(cookie => cookie.Key.StartsWith("ASPSESSIONID")) .Select(cookie => string.Join("=", cookie.Key, cookie.Value))); if (aspSessionCookies.Length == 0) { // logs can be found in /ckfinder/App_Data/logs LoggerManager.GetLoggerForCurrentClass().Info("No ASP session cookie found"); // don't make an extra request to the connector.asp, there's no session initiated return new JObject(); } //replace this URL with your connector.asp's var publicAspSessionConnectorUrl = new Uri("http://myaspwebsite.com/connector.asp"); var localSafeAspSessionConnectorUrl = new UriBuilder(publicAspSessionConnectorUrl) { Host = requestContext.LocalIpAddress }; using (var wCli = new WebClient()) try { wCli.Headers.Add(HttpRequestHeader.Cookie, aspSessionCookies); wCli.Headers.Add(HttpRequestHeader.Host, publicAspSessionConnectorUrl.Host); return JObject.Parse(wCli.DownloadString(localSafeAspSessionConnectorUrl.Uri)); } catch (Exception ex) // returning an empty JObject object in any fault { // logs can be found in /ckfinder/App_Data/logs LoggerManager.GetLoggerForCurrentClass().Error(ex); return new JObject(); } } public Task AuthenticateAsync(ICommandRequest commandRequest, CancellationToken cancellationToken) { var aspSessionState = GetAspSessionState(commandRequest); var roles = new List(); var isEditor = aspSessionState.GetNullSafeValue("isEditor", false); var isMember = aspSessionState.GetNullSafeValue("isMember", false); if (isEditor) roles.Add("editor"); if (isMember) roles.Add("member"); var isAuthenticated = isEditor || isMember; var user = new User(isAuthenticated, roles); return Task.FromResult((IUser)user); } } public static class JObjectExtensions { // an extension method to help case insensitive lookups with a default value to get avoid NullReferenceException public static T GetNullSafeValue(this JObject jobj, string key, T defaultValue = default(T)) { dynamic val = jobj.GetValue(key, StringComparison.OrdinalIgnoreCase); if (val == null) return defaultValue; return (T)val; } } } 

现在你应该有一个有效的CKFinder连接器。 如果需要,可以更改AuthenticateAsync方法中的逻辑,并查看CKFinder如何处理Classic ASP成员资格管理。

您是否使用ConnectorBuilder设置了自定义身份validation提供程序?

 public ConnectorBuilder ConfigureConnector() { var connectorBuilder = new ConnectorBuilder(); connectorBuilder.SetAuthenticator(new MyAuthenticator()); return connectorBuilder; } 

你可以在这里找到完整的例子: http : //docs.cksource.com/ckfinder3-net/configuration_by_code.html 。

UPDATE

另外,您应该在Startup类中注册ConnectorBuilder以将其添加到请求管道:

 public void Configuration(IAppBuilder appBuilder) { var connectorBuilder = ConfigureConnector(); var connector = connectorBuilder.Build(new OwinConnectorFactory()); appBuilder.Map("/CKFinder/connector", builder => builder.UseConnector(connector)); } 

所有这些都来自我之前提供的文档链接。