2018年5月15日火曜日

ルーティング

■.NetFramework
App_Start\RouteConfig.cs
routes.MapRoute(
    name: "Default",
    url: "{controller}/{action}/{id}",
    defaults: new
    {
        controller = "Home",
        action = "Index",
        id = UrlParameter.Optional
    }
);


■.Net Core
Startup.cs
app.UseMvc(routes =>
{
    routes.MapRoute(
        name: "default",
        template: "{controller=Home}/{action=Index}/{id?}");
});

2018年5月14日月曜日

認証の設定

■.Net Framework

App_Start\IdentityConfig.cs
manager.PasswordValidator = new PasswordValidator
{
    RequiredLength = 6,
    RequireNonLetterOrDigit = false,
    RequireDigit = true,
    RequireLowercase = true,
    RequireUppercase = true,
};

すでにある設定を変更する

■.Net Core
Startup.cs
services.Configure(options =>
{
    //パスワード設定
    options.Password.RequiredLength = 6;
    options.Password.RequireDigit = true;
    options.Password.RequireNonAlphanumeric = false;
    options.Password.RequireLowercase = false;
    options.Password.RequireUppercase = false;
});
オプションとして新たに追加する

2017年3月13日月曜日

回帰直線のメモ

using System;
using System.Collections.Generic;

namespace WindowsFormsApplication1
{
    public class RegressionLine
    {
        public RegressionLine(Listdata)
        {
            this.Data = data;

            this.CalcSlopeIntercept();
        }

        private List Data { get; set; }

        public double Slope { get; private set; }

        public double Intercept { get; private set; }

        private void CalcSlopeIntercept()
        {
            double sumXY = 0;
            double sumX = 0;
            double sumY = 0;
            double sumX2 = 0;

            for (int i = 0; i < this.Data.Count; i++)
            {
                sumXY += Data[i].X * this.Data[i].Y;
                sumX += Data[i].X;
                sumY += this.Data[i].Y;
                sumX2 += Math.Pow(Data[i].X, 2);
            }

            this.Slope = (this.Data.Count * sumXY - sumX * sumY) / (this.Data.Count * sumX2 - Math.Pow(sumX, 2));
            this.Intercept = (sumX2 * sumY - sumXY * sumX) / (this.Data.Count * sumX2 - Math.Pow(sumX, 2));
        }

        public double GetExpectancyX(double y)
        {
            return (y - this.Intercept) / this.Slope;
        }

        public double GetExpectancyY(double x)
        {
            return this.Slope * x + this.Intercept;
        }
    }
}

2017年2月21日火曜日

大文字、小文字を無視してDistinct

小文字でグループ化したデータのうち最初のデータを取り出す

using System;
using System.Collections.Generic;
using System.Linq;

public class Hello{
    public static void Main(){
        // Here your code !
        List data = new List{"CSharp", "CSHARP", "csharp"};
        
        foreach(string d in data.GroupBy(d => d.ToLower()).Select(d => d.First())){
            Console.WriteLine(d);
        }
        
    }
}

実行すると CSharpが出力される

2017年2月19日日曜日

デフォルトで許可されていないURLの文字

例えば、ブログなんかをイメージしてもらえればよいのだがタグのリンクを以下のようにしたとする

/Blog/Tags/ASP.NET
/Blog/Tags/SQL+Server

.や半角スペースのエンコードした+なんかが含まれているとアクセスするとエラーになる。

■.を許可する。
認識するために/Web.configに、以下を追加する

  
    
      
    
  


まずは対象のパスを指定 今回は/Blog/Tags/の次の部分を対象とするので /Blog/Tags/* としてある。


■+を許可する
+を含んだパスにアクセスすると
以下のエラーが出る
要求フィルター モジュールが、ダブル エスケープ シーケンスを含む要求を拒否するように構成されています。

可能性のある原因:
要求にダブル エスケープ シーケンスが含まれていました。要求フィルターはダブル エスケープ シーケンスを拒否するように Web サーバーで構成されています。

対処方法:
applicationhost.config または web.confg ファイルにある configuration/system.webServer/security/requestFiltering@allowDoubleEscaping 設定を確認します。

以下設定を追加すると許可される

  
    
      
    
  

2017年2月12日日曜日

ASP.NET MVC5メモ

バインディング

ViewのデータをPostする際に、Nameの名前が所定のルールに従っていれば自動的に
バインドしてくれるので、Controllerの引数から受け取ることができます。


基本は、InputタグのNameに クラス名.プロパティとかけばバインドしてくれます。
あとは、プロパティがリストだという場合は、 クラス名.プロパティ[インデックス]
クラス自体がリストで受け取るのであれば クラス名[インデックス].プロパティ
といった感じでかけば受け取ることができます。

わかりやすくするため、ViewでHTMLをハードコードします。

Models/Sample.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;

namespace SampleCode.Models
{
    public class Sample
    {
        public int ID { get; set; }
        public string Name { get; set; }
    }
}

IDとNameを持つだけのクラスです。

適当にHomeという名前のControllerを作成して以下のように書きました

Controllers/HomeController.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.Mvc;

namespace SampleCode.Controllers
{
    public class HomeController : Controller
    {
        // GET: Home
        public ActionResult Create()
        {
            return View();
        }

        [HttpPost]
        public ActionResult Create(Models.Sample sample)
        {
            return View();
        }
    }
}
ブレイクポイントを設定して確認します。

Views/Home/Create.cshtml
@{
    ViewBag.Title = "Create";
}

Create

@using (Html.BeginForm()) { @Html.AntiForgeryToken() }




@modelにクラスが設定されていれば、Nameのところでクラス名を省略できます。
Views/Home/Create.cshtml
@model SampleCode.Models.Sample

@{
    ViewBag.Title = "Create";
}

Create

@using (Html.BeginForm()) { @Html.AntiForgeryToken() }



今度は、クラス内にListがある時

Models/Sample.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;

namespace SampleCode.Models
{
    public class Sample
    {
        public int ID { get; set; }
        public string Name { get; set; }
        public List Memo { get; set; }
    }
}



Views/Home/Create.cshtml
@model SampleCode.Models.Sample

@{
    ViewBag.Title = "Create";
}

Create

@using (Html.BeginForm()) { @Html.AntiForgeryToken() }

リストはプロパティ名に[インデックス]番号つければバインドできます




今度は、Dictionaryをモデルに持っている時です
Models/Sample.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;

namespace SampleCode.Models
{
    public class Sample
    {
        public int ID { get; set; }
        public string Name { get; set; }
        public Dictionary Hash { get; set; }
    }
}


Controllers/HomeController.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.Mvc;

namespace SampleCode.Controllers
{
    public class HomeController : Controller
    {
        // GET: Home
        public ActionResult Create()
        {
            return View();
        }

        [HttpPost]
        public ActionResult Create(Models.Sample sample)
        {
            return View();
        }
    }
}

Views/Home/Create.cshtml
@model SampleCode.Models.Sample

@{
    ViewBag.Title = "Create";
}

Create

@using (Html.BeginForm()) { @Html.AntiForgeryToken() }

KeyValueのうち、Keyは inputのhiddenに、Valueは取得したいinput要素のNameに指定します。
KeyとValueをペアリングするために Nameにプロパティ名[文字列] が一致する者同士を KeyValueのペアとみなします。

<input type = "hidden" name="プロパティ名[文字列].key" value="キー名" />
<input type = "text" name="プロパティ名[文字列].value" value="値" />

[文字列]はループ処理とかを考えると数字が来やすいけども
keyとvalueをペアリングするための識別子なので、任意の文字を指定できます



今度は、Controllerで受け取る引数をリスト(List)にしてみます。

Models/Sample.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;

namespace SampleCode.Models
{
    public class Sample
    {
        public int ID { get; set; }
        public string Name { get; set; }
    }
}

Controllers/HomeController.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.Mvc;

namespace SampleCode.Controllers
{
    public class HomeController : Controller
    {
        // GET: Home
        public ActionResult Create()
        {
            return View();
        }

        [HttpPost]
        public ActionResult Create(List list)
        {
            return View();
        }
    }
}

Viewes/Home/Create.cshtml
@model SampleCode.Models.Sample

@{
    ViewBag.Title = "Create";
}

Create

@using (Html.BeginForm()) { @Html.AntiForgeryToken() }
基本は、クラス名[数字].プロパティ ですが、modelで明示してあるので省略してあるだけです。



クラス内でListを使い、そのクラスをリストで受けるとなると、今までの方法を組み合わせるだけです
Models/Sample.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;

namespace SampleCode.Models
{
    public class Sample
    {
        public int ID { get; set; }
        public string Name { get; set; }
        public List Memo { get; set; }
    }
}

Controllers/HomeController.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.Mvc;

namespace SampleCode.Controllers
{
    public class HomeController : Controller
    {
        // GET: Home
        public ActionResult Create()
        {
            return View();
        }

        [HttpPost]
        public ActionResult Create(List list)
        {
            return View();
        }
    }
}

Views/Home/Create.cshtml
@model SampleCode.Models.Sample

@{
    ViewBag.Title = "Create";
}

Create

@using (Html.BeginForm()) { @Html.AntiForgeryToken() }

何が複数なのかを考えればクラスに[数字]をつけるかプロパティに[数字]をつけるか明確ですね


ちなみに、クラスのインスタンスに、一加工してから格納したいので
ひとまずリストで受け取りたいなんて場合、いちいちクラスを作らなくてもバインドしてくれます
Models/Sample.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;

namespace SampleCode.Models
{
    public class Sample
    {
        public int ID { get; set; }
        public string Name { get; set; }
    }
}

Controllers/HomeController.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.Mvc;

namespace SampleCode.Controllers
{
    public class HomeController : Controller
    {
        // GET: Home
        public ActionResult Create()
        {
            return View();
        }

        [HttpPost]
        public ActionResult Create(List list, List hoge)
        {
            return View();
        }
    }
}
Modelに定義せずに List を用意。
名前をhogeにしたので、Viewにもhogeの名前でnameにつけます。

Views/Home/Create.cshtml
@model SampleCode.Models.Sample

@{
    ViewBag.Title = "Create";
}

Create

@using (Html.BeginForm()) { @Html.AntiForgeryToken() }

これで、 List list にも List hogeにもバインドされます。