2013年12月21日 星期六

R.I.P. EntityDataSource


Tool:Visual Studio 2013 Ultimate
OS:Windows Server 2012
.NET Framework : 4.5.1



此篇文章探討的問題,有一新解法,請參考這篇文章 http://vmiv.blogspot.tw/2014/02/entitydatasource-resurrected.html

在VS2013 Web Forms Web Site使用EntityDataSource發生一些錯誤。重現錯誤:
  • New - ASP.NET WebForms Web Site
  • Add Edmx
image
  • from db
image

  • 選db
image
  • 選EF6
image
  • 選table
image
  • Add ASPX
image
  • 加一個GridView,新增Data Source
image
  • 選 Entity
image
  • 下一個畫面就GG了….
image
找尋許久,最後,根據這篇討論串 https://entityframework.codeplex.com/discussions/434936
結論就是EF6不支援 EntityDatasource了,Orz,要改用Entity Framework 5版本才行。舊專案沒事不要亂升級版本啊!!
  • 重複上面的步驟,但選Entity Framework 5版:
image
  • 在相同的地方,一樣GG….. Orz * 2,
不是說Entity Framework 5有支援的嗎??
試了半天,有個愚笨的解法:
  • 預設使用T4產生Entity Framework相關類別,先改回Legacy ObjectContext,刪到所有TT檔:
image
  • 設定Code Generation Strategy為Legacy ObjectContext
image
  • 重Build
  • GridView->Choose Data Source->Entity
image
  • 這回就沒顯示錯誤訊息了
image
image
  • 工具產生的tag如下
<asp:GridView ID="GridView1" runat="server" DataSourceID="EntityDataSource1"></asp:GridView>
   <asp:EntityDataSource runat="server" ID="EntityDataSource1" DefaultContainerName="pubsEntities" ConnectionString="name=pubsEntities" EnableFlattening="False" EntitySetName="stores"></asp:EntityDataSource>
  • RUN ASPX也沒問題
image
  • 若想要改回用T4範本,在此時可以選 Add Code Generation Item
image
  • 加入T4 範本
image
  • 可正常執行
image
  • 不過,設計工具就又失效了,後續想修改就自己敲Tag吧   Orz…誰記得這些tag要怎麼敲啊?
image

2013年12月20日 星期五

localdb readonly問題

 

Tool:Visual Studio 2013 Ultimate
OS:Windows Server 2012
.NET Framework : 4.5.1

在VS2013 使用localdb存取檔案型資料庫,常常會有readonly的問題,從工具看起來如下:

image

你需要授權給登入OS的帳號:

icacls 資料庫檔名前置字串*.* /grant "你的機器名稱\你的登入帳號":(F)

例如:
icacls pubs*.* /grant "myServer\Administrator":(F)

image

關掉Visual Studio 2013,再重開啟。要等一下下(好像還蠻久的,感覺過了幾分鐘,Visual Studio 開開關關好幾次.. ORZ),再做refresh,就會生效了:

image

2013年12月17日 星期二

jQuery Code Snippet

 


Tool:Visual Studio 2012 Ultimate
OS:Windows 8
.NET Framework : 4.5

在Visual Studio 撰寫jQuery程式時,可以利用擴充程式提供的Code Snippet功能,來快速完成程式碼。

在Visual Studio – Tools – Extensions and Updates,搜尋jQuery後下載安裝:

image

安裝:

image

image

在撰寫jQuery時,就可以按CTRL+K,CTRL+X叫出Code Snippet

image

找到想用的程式片段插入

image

產生的code:

image

或輸入快速鍵,如jqFind,按Tab兩次

image

產生程式:

image

JSON 資料轉C# 類別

 

Tool:Visual Studio 2012 Ultimate
OS:Windows 8
.NET Framework : 4.5

若有一個ASPX檔案回傳JSON格式的字串資料:

<%@ Page Language="C#" %>
<script runat="server">
  protected void Page_Load( object sender , EventArgs e ) {
    string json = "{'Employee':[{'ID':1,'Name':'Mary'},{'ID':2,'Name':'Candy'}]}";
    Response.Write( json );   
  }
</script>

ASPX網頁執行時,送出以下資料到Browser

image

copy所有字串:

image

在Visual Studio工具,開啟任意C#類別設計畫面:

image

選Paste Special –> Paste JSON As Classes

image

Visual Studio 會自動根據JSON資料產生出對應類別,以存放JSON資料:

image

2013年12月5日 星期四

jQuery Mobile - 關於 changeHash

Tool:Visual Studio 2012 Ultimate
OS:Windows 8
.NET Framework : 4.5

jQuery Mobile的$.mobile.changePage()方法有一個changeHash選項可以設定。changeHash預設為true,用來指定是否更新瀏覽歷程(history),若設為true會更新歷程(history),增加一筆歷史記錄,若設為false,新載入的頁面會取代目前瀏覽器歷程(browser history),因此未來不能用back按鈕回到此頁。

例如以下範例HTML有兩個Page:Page1與Page2,Page1包含一個<a>利用程式叫用changePage()方法跳到Page2

<!DOCTYPE html>
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
    <title></title>
    <meta name="viewport" content="width=device-width, initial-scale=1" />
    <link href="Content/jquery.mobile-1.2.0.min.css" rel="stylesheet" />
    <script src="Scripts/jquery-1.8.3.min.js"></script>
    <script src="Scripts/jquery.mobile-1.2.0.min.js"></script>
    <script>
        $(function () {
            $("#goPage2").click(
                function () {
                    $.mobile.changePage("#Page2", {
                        changeHash: false
                    });
                });
        });
    </script>
</head>
<body>
    <div data-role="page" id="Page1">
        <div data-role="content">
            <p>
                <a id="goPage2" data-role="button">跳到Page2</a>
            </p>
        </div>
    </div>
    <div data-role="page" id="Page2">
        <div data-role="content">
            Page2
        </div>
    </div>
</body>
</html>

changeHash設為false時執行:

image

跳到Page2,則回上一頁的按鈕是disable的,不能點選:

image

將changeHash改為true,執行,則可以點選回上一頁的按鈕:

image

2013年12月4日 星期三

Tips: IIS 8 Express ASP.NET暫存資料夾

Tool:Visual Studio 2012 Ultimate
OS:Windows 8
.NET Framework : 4.5

ASP.NET網站,當網頁執行時,會動態編譯成dll (Web Site類型),然後放到暫存資料夾(Temporary ASP.NET Files),若我們要知道資料夾在哪,可以在網頁中加入以下程式

protected void Page_Load( object sender , EventArgs e ) {
   Response.Write( HttpRuntime.CodegenDir );
}

以下是在Windows 8 執行的結果:

image

2013年12月2日 星期一

使用PreApplicationStartMethod動態註冊HTTP Module

 

Tool:Visual Studio 2013 Ultimate
OS:Windows Server 2012
.NET Framework : 4.5.1

在ASP.NET 4 版,新增一個PreApplicationStartMethodAttribute,可以指定一個方法,在Global.asax Application_Start事件之前執行,因此此方法不能夠存取到HttpApplication或HttpContext物件。

利用PreApplicationStartMethodAttribute可以在執行時期組態ASP.NET Runtime的運作,例如動態註冊Http Module。

適用於ASP.NET Web Application類型專案,不適用於ASP.NET Web Site。

以下說明使用ASP.NET Web Application專案動態註冊Http Module步驟

  • 建立ASP.NET Web Forms專案,New ASP.NET Web Application

image

  • 建立Empty- Web Forms專案

image

  • 加入一個ASP.NET Module到專案

image

  • Add Code,在每個Request結束時,自動加入Copyright說明到網頁

 

using System;
using System.Web;

namespace MyWebApp {
  public class Copyright : IHttpModule {
    /// <summary>
    /// You will need to configure this module in the Web.config file of your
    /// web and register it with IIS before being able to use it. For more information
    /// see the following link: http://go.microsoft.com/?linkid=8101007
    /// </summary>
    #region IHttpModule Members

    public void Dispose( ) {
      //clean-up code here.
    }

    public void Init( HttpApplication context ) {
      // Below is an example of how you can handle LogRequest event and provide
      // custom logging implementation for it
      context.LogRequest += new EventHandler( OnLogRequest );
      context.EndRequest += context_EndRequest;
    }

    void context_EndRequest( object sender , EventArgs e ) {
      HttpApplication application = ( HttpApplication ) sender;
      HttpContext context = application.Context;
      context.Response.Write( "<h3>Copyright by MiMiCat</h3>" );       
    }

    #endregion

    public void OnLogRequest( Object source , EventArgs e ) {
      //custom logging logic can go here
    }
  }
}

  • 使用NuGet下載

image

  • 加入PreApplicationStart類別
image
  • 加入code,動態註冊Http Module

using Microsoft.Web.Infrastructure.DynamicModuleHelper;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;

namespace MyWebApp {
  public class PreApplicationStart {
    public static void Start( ) {

     DynamicModuleUtility.RegisterModule( typeof( Copyright ) );
    }
  }
}

  • 修改AssemblyInfo.cs,加入PreApplicationStartMethodAttribute:

using MyWebApp;
using System.Reflection;
using System.Runtime.CompilerServices;
using System.Runtime.InteropServices;
using System.Web;

[assembly: PreApplicationStartMethod( typeof( PreApplicationStart ) , "Start" )]

  • 加入網頁測試

image

  • 直接執行網頁,便套用Http Module,加上copyright

image

  • PS: 動態註冊HTTP Module的動作不能在Applicaiton_Start事件處理,否則會得到以下錯誤:

image

使用ScriptManager管理Script

 

Tool:Visual Studio 2013 Ultimate
OS:Windows Server 2012
.NET Framework : 4.5.1

 

這是自ASP.NET4.5版就新增的新功能,在ASP.NET Web Forms網站之中,可以利用ScriptManager來管理JavaScript,例如jQuery,讓引用更方便。

  • 建立一個Web Site

image

  • 使用NuGet下載jQuery,目前版本2.0.3

image

  • 加入Global Application Class

image

  • Add Code:

void Application_Start ( object sender , EventArgs e ) {
    // Code that runs on application startup
    ScriptManager.ScriptResourceMapping.AddDefinition (
           "jquery" ,
           new ScriptResourceDefinition {
               Path = "~/Scripts/jquery-2.0.3.min.js" ,
               DebugPath = "~/Scripts/jquery-2.0.3.js" ,
           } );
}

  • 加入ASPX

image

  • 加入ScriptManager,引用jQuery,後續就可以直接使用jQuey程式碼。若web.config中設定debug為true,則下載jquery-2.0.3.js,若設定debug為false,則下載jquery-2.0.3.min.js

 

<%@ Page Language="C#" %>

<!DOCTYPE html>

<script runat="server">

</script>

<html xmlns="http://www.w3.org/1999/xhtml">
<head runat="server">
    <title></title>
</head>
<body>
    <form id="form1" runat="server">
    <div>
        <asp:ScriptManager ID="ScriptManager1" runat="server">
            <Scripts>
                <asp:ScriptReference Name="jquery" />
            </Scripts>
        </asp:ScriptManager>

       
    </div>
    </form>
    <script>
       $(function () {
           alert('Hello from jQuery');
       });

    </script>
</body>
</html>

  • 使用Chrome Browser Test,一執行ASPX就會執行jQuery 程式碼,按F12開啟Chrome除錯工具,檢視,下載的是min版本,因debug設為false

image

  • 將debug設為true,則重新refresh,下載的是除錯版

image

  • 改用CDN,修改global.asax,加入CdnPath與CdnDebugPath:

void Application_Start ( object sender , EventArgs e ) {
       // Code that runs on application startup
       ScriptManager.ScriptResourceMapping.AddDefinition (
              "jquery" ,
              new ScriptResourceDefinition {
                  Path = "~/Scripts/jquery-2.0.3.min.js" ,
                  DebugPath = "~/Scripts/jquery-2.0.3.js" ,
                  CdnPath = http://code.jquery.com/jquery-2.0.3.min.js,
                  CdnDebugPath =
http://code.jquery.com/jquery-2.0.3.js
                
              } );
   }

  • ScriptManager啟用CDN,EnableCdn="true"

<%@ Page Language="C#" %>

<!DOCTYPE html>

<script runat="server">

</script>

<html xmlns="http://www.w3.org/1999/xhtml">
<head runat="server">
    <title></title>
</head>
<body>
    <form id="form1" runat="server">
    <div>
        <asp:ScriptManager ID="ScriptManager1" runat="server" EnableCdn="true">
            <Scripts>
                <asp:ScriptReference Name="jquery" />
            </Scripts>
        </asp:ScriptManager>
       
    </div>
    </form>
    <script>
       $(function () {
           alert('Hello from jQuery');
       });
    </script>
</body>
</html>

  • 重新執行網頁,檔案便從CDN下載,

image

  • 若CDN上的Script無法下載下來,想要改用本機的script時,可以使用LoadSuccessExpression 設定一個運算式(Expression),用來偵測CDN上的JavaScript是否成功下載,例如修改global.asax,設定錯誤的CDN路徑,並加上判斷式


void Application_Start ( object sender , EventArgs e ) {
    // Code that runs on application startup
    ScriptManager.ScriptResourceMapping.AddDefinition (
           "jquery" ,
           new ScriptResourceDefinition {
               Path = "~/Scripts/jquery-2.0.3.min.js" ,
               DebugPath = "~/Scripts/jquery-2.0.3.js" ,
               CdnPath = "http://code.jquery.com/jquery-2.0.3.minxxx.js" ,
               CdnDebugPath = "
http://code.jquery.com/jquery-2.0.3xxx.js",
               LoadSuccessExpression="typeof(window.jQuery) !== 'undefined'"
             
           } );
}

  • 執行時,CDN下載錯誤,則自動從Script下載

image

總網頁瀏覽量