Skip to content

Commit

Permalink
Merge pull request aspnetboilerplate#1 from aspnetboilerplate/master
Browse files Browse the repository at this point in the history
get all updates
  • Loading branch information
carldai0106 committed Sep 22, 2015
2 parents 3da5a7d + 928d656 commit cd3b9e6
Show file tree
Hide file tree
Showing 256 changed files with 6,637 additions and 1,906 deletions.
1 change: 1 addition & 0 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@

ASP.NET Boilerplate
===================

Expand Down
11 changes: 6 additions & 5 deletions doc/WebSiteContents/_empty.html
Original file line number Diff line number Diff line change
Expand Up @@ -3,18 +3,19 @@

<head>
<meta content="text/html; charset=utf-8" http-equiv="Content-Type" />
<title>Entities</title>
<title>ASP.NET Boilerplate</title>
<link type="text/css" rel="stylesheet" href="bootstrap.min.css" />
</head>

<body>

<ul>
<li><a href="#DocIntro">Introduction</a></li>
</ul>
<h3 id="DocIntro">Introduction</h3>
<div class="document-contents">

<h3>Introduction</h3>
<p>....</p>

</div>

</body>

</html>
3 changes: 2 additions & 1 deletion doc/WebSiteContents/abp-session.html
Original file line number Diff line number Diff line change
Expand Up @@ -24,11 +24,12 @@ <h3 id="DocIntroduction">Introduction</h3>

<div class="bs-callout bs-callout-warning">
<h4>About IAbpSession</h4>
<p><span class="auto-style1">IAbpSession</span>
<p>IAbpSession
interface must be implemented in order to get actual session informations. While you can
implement it in your own way, it's fully implemented in <strong>module-zero</strong>
project.</p>
</div>

<p>IAbpSession is also fully integrated and used by other structures in ASP.NET
Boilerplate (setting system and authorization system for instance).</p>

Expand Down
39 changes: 29 additions & 10 deletions doc/WebSiteContents/authorization.html
Original file line number Diff line number Diff line change
Expand Up @@ -14,15 +14,8 @@

<body>

<ul>
<li><a href="#DocIntroduction">Introduction</a></li>
<li><a href="#DocDefinePermission">Defining permissions</a></li>
<li><a href="#DocCheckPermission">Checking permissions</a><ul>
<li><a href="#DocUsingAbpAuthorize">Using AbpAuthorize attribute</a></li>
<li><a href="#DocUsingPermissionChecker">Using IPermissionChecker</a></li>
</ul>
</li>
</ul>
<div class="document-contents">

<h3 id="DocIntroduction">Introduction</h3>
<p>Almost all enterprise applications use authorization in some level.
Authorization is used to check if a user is allowed to perform some specific
Expand All @@ -33,7 +26,7 @@ <h4>About IPermissionChecker</h4>
<p>Authorization system uses <strong>IPermissionChecker</strong> to check
permissions. While you can
implement it in your own way, it's fully implemented in <strong>module-zero</strong>
project. If it's not implemented, NullPermissionChecker is used that grants all
project. If it's not implemented, NullPermissionChecker is used which grants all
permissions to everyone.</p>
</div>

Expand Down Expand Up @@ -161,6 +154,32 @@ <h4 id="DocUsingPermissionChecker">Using IPermissionChecker</h4>
ApplicationService</strong> base class injects and defines PermissionChecker
property. Thus, permission checker can be used without injecting in application
service classes.</p>
<h4>In Razor Views</h4>
<p>Base view class defines IsGranted method to check if current user has a
permission. Thus, we can conditionally render the view. Example:</p>
<pre lang="xml">@if (IsGranted("Administration.UserManagement.CreateUser"))
{
&lt;button id=&quot;CreateNewUserButton&quot; class=&quot;btn btn-primary&quot;&gt;&lt;i class=&quot;fa fa-plus&quot;&gt;&lt;/i&gt; @L(&quot;CreateNewUser&quot;)&lt;/button&gt;
}</pre>

<h4>Client Side (Javascript)</h4>

<p>In the client side, we can use API defined in <strong>abp.auth</strong>
namespace. In most case, we need to check if current user has a specific
permission (with permission name). Example:</p>
<pre lang="js">abp.auth.hasPermission('Administration.UserManagement.CreateUser');</pre>

<p>You can also use <strong>abp.auth.grantedPermissions</strong> to get all
granted permissions or <strong>abp.auth.allPermissions</strong> to get all
available permission names in the application. Check <strong>abp.auth</strong>
namespace on runtime for others.</p>

<h3>Permission Manager</h3>
<p>We may need to definitions of permission. <strong>IPermissionManager</strong>
can be <a href="/Pages/Documents/Dependency-Injection">injected</a> and used in
that case. </p>

</div>

</body>

Expand Down
115 changes: 115 additions & 0 deletions doc/WebSiteContents/caching.html
Original file line number Diff line number Diff line change
@@ -0,0 +1,115 @@
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">

<head>
<meta content="text/html; charset=utf-8" http-equiv="Content-Type" />
<title>ASP.NET Boilerplate</title>
<link type="text/css" rel="stylesheet" href="bootstrap.min.css" />
</head>

<body>

<div class="document-contents">

<h3>Introduction</h3>

<p>ASP.NET Boilerplate provides an abstraction for caching. It internally uses this cache abstraction. While default
implementation uses
<a href="https://msdn.microsoft.com/en-us/library/system.runtime.caching.memorycache(v=vs.110).aspx?f=255&amp;MSPPError=-2147217396">
MemoryCache</a>, it can be implemented and changable for any other caching
provider.</p>

<h3>ICacheManager</h3>

<p>Main interface for caching is <strong>ICacheManager</strong>. We can
<a href="/Pages/Documents/Dependency-Injection">inject</a> it and use it to get a cache. Example:</p>

<pre lang="cs">public class TestAppService : ApplicationService
{
private readonly ICacheManager _cacheManager;

public TestAppService(ICacheManager cacheManager)
{
_cacheManager = cacheManager;
}

public Item GetItem(int id)
{
//Try to get from cache
return _cacheManager
.GetCache(&quot;MyCache&quot;)
.Get(id.ToString(), () =&gt; GetFromDatabase(id)) as Item;
}

public Item GetFromDatabase(int id)
{
//... retrieve item from database
}
}</pre>
<p>In this sample, we're injecting <strong>ICacheManager</strong> and getting a
cache named <strong>MyCache</strong>.</p>

<div class="bs-callout bs-callout-warning">
<h4><strong>WARNING: </strong>GetCache Method</h4>
<p>Do not use GetCache method in your constructor. This may dispose the
Cache if your class is transient.</p>
</div>

<h3>ICache</h3>

<p>ICacheManager.<strong>GetCache</strong> method returns an <strong>ICache</strong>.
A cache is singleton (per cache name). It is created first time it's
requested, then returns always the same cache object. So, we can share same
cache with same name in different classes (clients).</p>
<p>In the sample code, we see simple usage of ICache.<strong>Get</strong>
method. It has two arguments:</p>
<ul>
<li><strong>key</strong>: A string unique key of an item in the cache.</li>
<li><strong>factory</strong>: An action which is called if there is no
item with the given key. Factory method should create and return the
actual item. This is not called if given key has present in the cache.</li>
</ul>
<p>ICache interface also has methods like <strong>GetOrDefault</strong>,
<strong>Set</strong>, <strong>Remove</strong> and <strong>Clear</strong>.
There are also <strong>async</strong> versions of all methods.</p>

<h3>ITypedCache</h3>

<p><strong>ICache </strong>interface works <strong>string</strong> as key
and <strong>object</strong> as value. <strong>ITypedCache</strong> is a
wrapper to ICache to provide <strong>type safe</strong>, generic cache. To
convert ICache to ITypedCache, we can use <strong>AsTyped</strong> extension method as shown
below:</p>
<pre lang="cs">ITypedCache&lt;int, Item&gt; myCache = _cacheManager.GetCache(&quot;MyCache&quot;)<strong>.AsTyped&lt;int, Item&gt;()</strong>;</pre>
<p>Then we can use Get method without converting and casting code.</p>

<h3>Configuration</h3>

<p>Default cache expire time is 60 minutes. It's sliding. So, if you don't use
an item in the cache for 60 minutes, it's automatically removed from the cache.
You can configure it for all caches or for a specific cache.</p>
<pre>//Configuration for all caches
Configuration.Caching.ConfigureAll(cache =&gt;
{
cache.DefaultSlidingExpireTime = TimeSpan.FromHours(2);
});

//Configuration for a specific cache
Configuration.Caching.Configure(&quot;MyCache&quot;, cache =&gt;
{
cache.DefaultSlidingExpireTime = TimeSpan.FromHours(8);
});</pre>
<p>This code should be placed
<a href="/Pages/Documents/Module-System#DocModulePreInit"><strong>PreInitialize</strong></a>
method of your module. With such a code, MyCache will have 8 hours expire time
while all other caches will have 2 hours.</p>
<p>Your configuration action is called once cache is first created (on
first request). Configuration is not restricted to DefaultSlidingExpireTime
only, since cache object is an ICache, you can use it's properties and methods
freely configure and initialize it.</p>

</div>

</body>

</html>
50 changes: 18 additions & 32 deletions doc/WebSiteContents/data-filters.html
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,6 @@

<head>
<meta content="text/html; charset=utf-8" http-equiv="Content-Type" />
<title>Entities</title>
<link type="text/css" rel="stylesheet" href="bootstrap.min.css" />
<style type="text/css">
.auto-style1 {
Expand All @@ -14,20 +13,7 @@

<body>

<ul>
<li><a href="#DocIntro">Introduction</a></li>
<li><a href="#DocPredefinedFilters">Pre-defined filters</a><ul>
<li><a href="#DocSoftDelete">ISoftDelete</a></li>
<li><a href="#DocMustHaveTenant">IMustHaveTenant</a></li>
<li><a href="#DocMayHaveTenant">IMayHaveTenant</a></li>
</ul>
</li>
<li><a href="#DocDisableFilters">Disable filters</a></li>
<li><a href="#DocEnableFilters">Enable filters</a></li>
<li><a href="#DocSetFilterParams">Setting filter parameters</a></li>
<li><a href="#DocDefineCustomFilters">Defining custom filters</a></li>
<li><a href="#DicOtherORMs">Other ORMs</a></li>
</ul>
<div class="document-contents">

<h3 id="DocIntro">Introduction</h3>
<p>It's common to use the <a href="/Pages/Documents/Entities#DocSoftDelete">
Expand All @@ -41,13 +27,6 @@ <h3 id="DocIntro">Introduction</h3>
to automatically filter queries based on some rules. There are some pre-defined
filters, but also you can create your own filters.</p>

<div class="bs-callout bs-callout-warning">
<h4>Only for EntityFramework</h4>
<p>ASP.NET Boilerplate data filtering is implemented just for
EntityFramework. Not available for other ORM tools yet. See other ORMs
section at the end of the document.</p>
</div>

<h3 id="DocPredefinedFilters">Pre-defined filters</h3>

<h4 id="DocSoftDelete">ISoftDelete</h4>
Expand Down Expand Up @@ -104,11 +83,11 @@ <h4 id="DocMustHaveTenant">IMustHaveTenant</h4>
<p>If you are building multi-tenant applications (store all tenant datas in
single database), you definitely do not want a tenant accidently see other's
data. You can implement <strong>IMustHaveTenant</strong> in that case. Example:</p>
<pre lang="cs">public class Product : IMustHaveTenant
<pre lang="cs">public class Product : Entity, <strong>IMustHaveTenant</strong>
{
public virtual int TenantId { get; set; }
<strong>public int TenantId { get; set; }</strong>

public virtual string Name { get; set; }
public string Name { get; set; }
}</pre>
<p><strong>IMustHaveTenant</strong> defines <strong>TenantId </strong>to
distinguish different tenant entities. ASP.NET Boilerplate uses
Expand All @@ -131,11 +110,11 @@ <h4 id="DocMayHaveTenant">IMayHaveTenant</h4>
be owned by a tenant or the host), you can use IMayHaveTenant filter. <strong>
IMayHaveTenant</strong> interface defines <strong>TenantId</strong> but it's <strong>
nullable</strong>.</p>
<pre lang="cs">public class Product : IMayHaveTenant
<pre lang="cs">public class Role : Entity, <strong>IMayHaveTenant</strong>
{
public virtual int? TenantId { get; set; }
<strong>public int? TenantId { get; set; }</strong>

public virtual string Name { get; set; }
public string RoleName { get; set; }
}</pre>
<p>A <strong>null</strong> value means this is a <strong>host</strong> entity, a <strong>non-null</strong> value means this entity
owned by a <strong>tenant</strong> which's Id is the TenantId. ASP.NET Boilerplate uses
Expand Down Expand Up @@ -197,6 +176,10 @@ <h3 id="DocSetFilterParams">Setting filter parameters</h3>
<p>Another example: To set the tenantId value for the IMayHaveTenant filter:</p>
<pre lang="cs">CurrentUnitOfWork.SetFilterParameter(AbpDataFilters.MayHaveTenant, AbpDataFilters.Parameters.TenantId, 42);</pre>

<p>SetFilterParameter method also returns an IDisposable. So, we can use it in a
<strong>using</strong> statement to automatically <strong>restore the old value</strong>
after using statement.</p>

<h3 id="DocDefineCustomFilters">Defining custom filters</h3>
<p>To create a custom filter and integrate to ASP.NET Boilerplate, first we
should define an interface that will be implemented by entities which use this
Expand All @@ -219,6 +202,7 @@ <h3 id="DocDefineCustomFilters">Defining custom filters</h3>
<a href="https://github.com/jcachat/EntityFramework.DynamicFilters" target="_blank">EntityFramework.DynamicFilters</a></strong>, we use it's
rules to define the filter. In our <strong>DbContext </strong>class, we override
<strong>OnModelCreating </strong>and define filter as shown below:</p>

<pre lang="cs">protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
base.OnModelCreating(modelBuilder);
Expand Down Expand Up @@ -254,16 +238,18 @@ <h4>Documentation for EntityFramework.DynamicFilters</h4>
</p>
</div>

<p>We can create custom filters for security, active/passive entities,
multi-tenancy and so on.</p>
<p>We can create custom filters for security, active/passive entities and so on.</p>

<h3 id="DicOtherORMs">Other ORMs</h3>
<p>ASP.NET Boilerplate data filtering is implemented just for <strong>EntityFramework</strong>.
Not available for other ORM tools yet.&nbsp; But, actually, you can mimic it for
<p>ASP.NET Boilerplate data filtering is implemented for EntityFramework and
NHibernate.
Not available for other ORMs yet. But, actually, you can mimic it for
most cases as long as you're using <strong>repositories</strong> to get data. In this case, you
can create a custom <a href="/Pages/Documents/Repositories">repository</a> and
override <strong>GetAll</strong> and other data retrieve methods if needed.</p>

</div>

</body>

</html>
20 changes: 18 additions & 2 deletions doc/WebSiteContents/documents.html
Original file line number Diff line number Diff line change
Expand Up @@ -27,22 +27,24 @@ <h3>ABP Framework</h3>
<li><a href="/Pages/Documents/NLayer-Architecture">NLayer architecture</a></li>
<li><a href="/Pages/Documents/Module-System">Module system</a></li>
<li><a href="/Pages/Documents/Startup-Configuration">Startup configuration</a></li>
<li><a href="/Pages/Documents/Multi-Tenancy">Multi Tenancy</a></li>
</ul>
</li>
<li>Common structures</li>
<ul>
<li><a href="/Pages/Documents/Dependency-Injection">Dependency injection</a></li>
<li><a href="/Pages/Documents/Abp-Session">Session</a></li>
<li><a href="/Pages/Documents/Caching">Caching</a></li>
<li><a href="/Pages/Documents/Logging">Logging</a></li>
<li><a href="/Pages/Documents/Setting-Management">Setting management</a></li>
</ul>
<li>Domain layer<ul>
<li><a href="/Pages/Documents/Entities">Entities</a></li>
<li><a href="/Pages/Documents/Repositories">Repositories</a></li>
<li><a href="/Pages/Documents/Domain-Services">Domain services</a></li>
<li><a href="/Pages/Documents/Unit-Of-Work">Unit of work</a></li>
<li><a href="/Pages/Documents/EventBus-Domain-Events">Domain events (EventBus)</a></li>
<li><a href="/Pages/Documents/Data-Filters">Data filters</a></li>
<li><a href="/Pages/Documents/EventBus-Domain-Events">Domain events
(EventBus)</a></li>
</ul>
</li>
<li>Application layer<ul>
Expand Down Expand Up @@ -81,11 +83,25 @@ <h3>ABP Framework</h3>
<h3>Module Zero</h3>
<ul>
<li><a href="/Pages/Documents/Zero/Overall">Overall</a></li>
<li><a href="/Pages/Documents/Zero/Installation">Installation</a></li>
<li><a href="/Pages/Documents/Zero/Tenant-Management">Tenant management</a></li>
<li><a href="/Pages/Documents/Zero/User-Management">User management</a></li>
<li><a href="/Pages/Documents/Zero/Role-Management">Role management</a></li>
<li><a href="/Pages/Documents/Zero/Permission-Management">Permission management</a></li>
<li><a href="/Pages/Documents/Zero/Nuget-Packages">Nuget packages</a></li>
<li>
<a href="https://github.com/aspnetboilerplate/module-zero/releases" target="_blank">Change logs &amp; releases</a></li>
</ul>

<h3>Other</h3>
<ul>
<li>Chinese translation of ABP's documentation (thanks to contributors)<ul>
<li>Web site: <a href="http://www.cnblogs.com/mienreal/p/4528470.html">cnblogs.com/mienreal</a></li>
<li>Github: <a href="https://github.com/ABPFrameWorkGroup">github.com/ABPFrameWorkGroup</a></li>
</ul>
</li>
</ul>

</body>

</html>
Loading

0 comments on commit cd3b9e6

Please sign in to comment.