UWInfo Blog
發表新文章
[Join] | [忘記密碼] | [Login]
搜尋

搜尋意見
文章分類-#Author#
[所有文章分類]
所有文章分類
  • ASP.NET (48)
  • ASP.NET2.0 (15)
  • ASP.NET4.0 (34)
  • JavaScript (49)
  • jQuery (26)
  • FireFox (4)
  • UW系統設定 (3)
  • SQL (39)
  • SQL 2008 (25)
  • mirror (4)
  • SVN (4)
  • IE (9)
  • IIS (20)
  • IIS6 (1)
  • 閒聊 (7)
  • W3C (6)
  • 作業系統 (9)
  • C# (24)
  • CSS (12)
  • FileServer (1)
  • HTML 5 (11)
  • CKEditor (3)
  • UW.dll (13)
  • Visual Studio (16)
  • Browser (8)
  • SEO (1)
  • Google Apps (3)
  • 網站輔助系統 (4)
  • DNS (5)
  • SMTP (4)
  • 網管 (11)
  • 社群API (3)
  • SSL (4)
  • App_Inventor (1)
  • URLRewrite (2)
  • 開發工具 (6)
  • JSON (1)
  • Excel2007 (1)
  • 試題 (3)
  • LINQ (1)
  • bootstrap (0)
  • Vue (3)
  • IIS7 (3)
  • foodpanda (2)
  • 編碼 (2)
  • 資安 (3)
  • Sourcetree (1)
  • MAUI (1)
  • CMD (1)
  • my sql (1)
最新回應
  • Newtonsoft.Json.JsonConvert.DeserializeObject 失敗的情況
    test...more
  • dotnet ef dbcontext scaffold
    ...more
  • [ASP.NET] 利用 aspnet_regiis 加密 web.config
    ...more
  • IIS ARR (reverse proxy) 服務安裝
    ...more
  • [錯誤訊息] 請加入 ScriptResourceMapping 命名的 jquery (區分大小寫)
    ...more
  • 用 Javascript 跨網頁讀取 cookie (Cookie cross page, path of cookie)
    ...more
  • 線上客服 - MSN
    本人信箱被盜用以致資料外洩,是否可以請貴平台予以協助刪除該信箱之使用謝謝囉...more
  • 插入文字到游標或選取處
    aaaaa...more
  • IIS 配合 AD (Active Directory) 認証, 使用 .Net 6.0
    太感謝你了~~~你救了我被windows 認證卡了好幾天QQ...more
  • PostgreSQL 的 monitor trigger
    FOR EACH ROW 可能要改為 FOR EACH STATEMENT ...more
標籤
  • 192
  • login
  • ses
  • 500.19
  • net ORDER
  • MS8qKi9XQU
  • jq
  • 826
  • for
  • let
  • ti
  • SU
  • 專案 UNION A
  • c
  • 寬度
  • UNT
  • gmail
  • backup
  • http 錯èª
  • �
  • data
  • sing
  • ICSharpCod
  • unt ORDER
  • expression
  • ef
  • iis7 的設定匯
  • email,
  • ad
  • MVC
  • db.
  • if
  • [U2]
  • [t]
  • CCE-44186-
  • 1137
  • db
  • jQuery
  • 旋轉
  • image
  • 216
  • 202
  • WU
  • mdnN6Bp9
  • prop
  • block21211
  • 54
  • code
  • array
  • 6002121121
頁數 1 / 2 下一頁
搜尋 Data[t] 結果:
sessionStorage 跨分頁無法讀取
問題:
在開出新分頁後,無法讀取 sessionStorage 的資料


可能原因:
Chrome 某個版本,Stop cloning sessionStorage for windows opened with noopener
a标签_blank默认 rel="noopener" ,所以a标签需要加入rel=“opener” 而才能像window.open("同源页面")这种方式新开的页面会复制之前的sessionStorage


解決方法:
開新分頁前,加入 rel=“opener”參數即可。
例:
<a href="http://..." target="_blank" rel="opener">Link</a>

$(".hlkPrint").click(function () {
    $("form").setPostDataToStorage();

    $("form").attr("rel", "opener");
    $("form").attr("target", "_blank");
    $("form").attr("action", "xxxxx.aspx");
    $("form").submit();
});





參考:
面试官:你确定多窗口之间sessionStorage不能共享状态吗???
More...
Reiko, 2022/12/1 下午 05:57:23
CORS 實做 (jQuery + ASP.NET Core Web API)
加構獨立的 API Server 時, 要使用 Cookie 認証必需有以下條件:

1. Web Server 和 API Server 有相同的父網域.
2. Cookie 的網域指定到相同的父網域.
3. 在 API 的 Application 中允許 CORS Request, 需要修改 Startup.cs

3.1 在 ConfigureServices 中要加入  AddCors, 而且要記得 AllowCredentials()
        public void ConfigureServices(IServiceCollection services)
        {
            services.AddCors(options =>
            {
                options.AddPolicy(name: "Cors(PolicyName",
                                 builder =>
                                 {
                                     builder.WithOrigins("https://web1.yourdomain.com",
                                                         "https://web2.yourdomain.com")
                                     .AllowCredentials();
                                 });
            });

            services.AddControllers()
                .AddNewtonsoftJson(opt =>
                 opt.SerializerSettings.ContractResolver = new CamelCasePropertyNamesContractResolver());


3.2 在 Configure 中, 要加入 app.UseCors("Cors(PolicyName"), 記得要在  UseAuthorization() 之前.
        public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
        {
            app.UseExceptionMiddleware();

            app.UseHttpsRedirection();

            app.UseHttpsRedirection();

            app.UseRouting();

            app.UseCors(MyAllowSpecificOrigins);

            app.UseAuthorization();



4. 在 Client 端要加上 withCredentials: true
                            $.ajax({
                                url: apiRoot + "apiurl",
                                type: 'GET',
                                dataType: 'json', // 預期從server接收的資料型態
                                success: function (res) {
                                    console.log("success: ");
                                    console.log(res);                                    
                                },
                                xhrFields: {
                                    withCredentials: true
                                },
                                error: function (XMLHttpRequest, textStatus, errorThrown) {
                                    alert("發生錯誤");
                                }
                            });
More...
Bike, 2021/10/24 下午 05:17:54
試題
試說明以下程式碼的功用, 以及可改進的部份.


        string EndDate = Request["EndDate"];

        DataTable qtyControls = U2.SQL.DTFromSQL("Select YA00, PD00 from QtyControl Where EndDate > '" + EndDate + "' and SoldQty >= InitQty");

        var values = qtyControls.AsEnumerable().Select(r => "('" + r.Field<string>("YA00") + "','" + r.Field<string>("PD00") + "')").ToList();

        var sqls = new List<string>();
        sqls.Add("Delete StopSaleYAP;");

        int start = 0;        
        while(start < values.Count)
        {
            var end = start + 999;
            if(end > values.Count - 1)
            {
                end = values.Count;
            }

            sqls.Add("insert into StopSaleYAP(YA00, PD00) Values" + string.Join(",", values.GetRange(start, end)) + ";");

            start = end + 1;
        }

        U2.SQL.ExecuteSQL(string.Join("\r\n", sqls));


        public static bool IsErrorOrder(Order.Input.CheckValidOrder dto)
        {
            if (dto.OrderNos == null || dto.OrderNos.Count == 0)
            {
                return false;
            }

            var orderCount = dto.OrderNos.Count();
            var orders = NpreoOrderMain.GetList(dto.OrderNos);
            if (orders.Count != orderCount || !dto.OrderNos.Any(x => orders.Select(o => o.Order_No).Contains(x)))
            {
                return true;
            }
            return false;
        }


        var fu = Request.Files[0];
        fu.SaveAs(Server.MapPath("UploadFiles/") + fu.FileName);


--

基本題:

1. 對 Linq 熟嗎.

2. 對 ASP.Net 的 Cache  熟悉嗎.

3. 用過什麼 ORM, 試說明優缺點.

4. 試說明 MVC 的架構.

資安相關問題:

1. 試說明 SQL Injection

2. 試說明 Cross Site Injection.

3. 上傳檔案要注意的事項.

4. 試說明 cookie 的安全設定 ? same site, secure, http only.


前端相關加分題:

1. jQuery 或 Vue 熟悉嗎 ?

2. 試說明 RWD

3. 試說明 bootstrap

進階問題:

1. 試說明 Reflection

2. 試說明 Dependency Injection

3.  試說明 singleton vs static

4. 試單有兩個欄位 Id, Status (付款待確認: 1.1;  已付款: 2,  訂單已出貨: 3; 訂單取消中: 5; )
狀態 1.1 和 狀態 2 的訂單可取消,取消後改為狀態 5

客人要取消訂單,訂單編號為 123, 試說明程式執行的過程。
More...
Bike, 2020/10/24 上午 10:24:51
UW DB物件 GetAllDataFromBaseTableWithCache 會嚴重影響效能
UW -> DB 物件產生器會產生兩個function
GetAllDataFromBaseTableWithCache(string OrderFields = "_Default", bool IsCopy = true )
以及
Get物件名稱FromCachedDT(string Key)
-----------------------------------------------------------
設計上是希望將所有資料Cache在記憶體,然後前端直接抓出資料,不須到資料庫抓資料
理論上網頁速度應該比較佳,實際上卻發現是效能殺手

原因在於 GetAllDataFromBaseTableWithCache 是抓出整個table的資料放到 Cache
然後又做了一件事,當有人要資料時,會把整個 DataTable 做 Copy() 再 return
也就是說,當DataTable有數千筆資料列時
每叫用一次 "Get物件名稱FromCachedDT(string Key)" 就會把數千筆資料整個複製一次
再從複製出來的DataTable Select 出一列 return
------------------------------------------------------------
解決方法:
Get物件名稱FromCachedDT(string Key)  --> 改成一筆一筆資料做 Cache,這樣 Copy() 只會Copy一筆
實測上,原本頁面要跑1.8秒,調整後可以 0.4 秒就完成
-----------------------------------------------------------
結論:
PG產生器就把 GetAllDataFromBaseTableWithCache 拿掉吧
More...
darren, 2018/5/21 下午 03:17:00
比較程式碼
以前年輕不懂事, 寫了一些很遜的程式碼, 例如:

舊的程式碼:

        public static DataTable DTFromSQL(string Sql, string DBC = null, Int32 timeout = 0)
        {
            SqlDataAdapter DA = new SqlDataAdapter(Sql, GetDBC(DBC));

            DataTable DT = new DataTable();
            try
            {
                DA = new SqlDataAdapter(Sql, DBC);
                if (timeout > 0)
                {
                    DA.SelectCommand.CommandTimeout = timeout;
                }

                DA.Fill(DT);
            }
            catch (Exception ex)
            {
                throw new Exception(ex.ToString());
            }
            finally
            {
                DA.Dispose();
            }

            return DT;
        }


新的程式碼:
        public static DataTable DTFromSQL(string Sql, string DBC = null, Int32 timeout = 30)
        {
            using (var DA = new SqlDataAdapter(Sql, GetDBC(DBC)))
            {
                //不可為 null
                DataTable DT = new DataTable();

                DA.SelectCommand.CommandTimeout = timeout;

                DA.Fill(DT);

                return DT;
            }
        }


可以參考:
https://dotblogs.com.tw/yc421206/archive/2012/01/03/64154.aspx
 
More...
Bike, 2018/4/4 上午 07:56:39
幫輸出的 Excel 加上表頭 (NPOI, UW.ExcelPOI.DTToExcelAndWriteToClient)
我想大家一定會遇到要把資料匯出成 Excel 的需求. 以現有的工具, 大家想到作法大概都是先把資料放到一個 datatable 之中, 後叫用 UW.ExcelPOI.DTToExcelAndWriteToClient 就結束了.

前兩天遇到一個需求, 輸出的 Excel 要加上表頭, 如下圖



於是乎把  UW.ExcelPOI.DTToExcelAndWriteToClient 做了一些擴充, (其實應該說是幫 DTToWorkSheet 做了擴充), 過程如下.

1. 需求: 一個可以快速填入欄位的 Sub (method or function)
A. 每一個 Cell 可以設定內容(文字), 字型大小, 跨欄數, 對齊方式. (其它的未來再來擴充, 例如顔色).
B. 每一個 Row 由 Cell 組成, 由左到右.
C. 一次可以填多個 Row

2. 實作:
A. 先定義 Cell
    Public Class Cell
        Public Content As String
        Public Colspan As Int32 = 1
        Public Alignment As NPOI.SS.UserModel.HorizontalAlignment
        Public FontHeightInPoints As Int32 = 0

        Sub New(Content As String, Optional Colspan As Int32 = 1,
                Optional Alignment As NPOI.SS.UserModel.HorizontalAlignment = NPOI.SS.UserModel.HorizontalAlignment.General,
                Optional FontHeightInPoints As Int32 = 0)
            Me.Content = Content
            Me.Colspan = Colspan
            Me.Alignment = Alignment
            Me.FontHeightInPoints = FontHeightInPoints
        End Sub
    End Class


B. Row 的格式: 我想最直的覺的就是 List(of Cell) 了吧.

C. 多個 Row 的表示法: List(Of List(Of Cell))

D. 來把 Cell 填入 WorkSheet  吧, 
Public Shared Sub AddRows(WS As HSSFSheet, ltRows As List(Of List(Of Cell)), ByRef StartRow As Int32)

共有三個參數: WS  和 ltRows 應該不用解釋了. 最後一個 StartRow 用來指定插入資料的開始 Row.

E.  完整程式碼: (程式碼不看沒關係, 但要跳到 F. 重點講解哦)
Public Shared Sub AddRows(WS As HSSFSheet, ltRows As List(Of List(Of Cell)), ByRef StartRow As Int32)
        Dim WR As HSSFRow
        If ltRows IsNot Nothing Then
            For Each ltRow As List(Of Cell) In ltRows
                WR = WS.CreateRow(StartRow)
                Dim C As Int32 = 0
                For Each cell As Cell In ltRow
                    Dim ic As NPOI.SS.UserModel.ICell = WR.CreateCell(C)
                    ic.SetCellValue(cell.Content)

                    Dim cs As NPOI.SS.UserModel.ICellStyle = WS.Workbook.CreateCellStyle()
                    cs.Alignment = cell.Alignment
                    If cell.FontHeightInPoints > 0 Then
                        Dim oFont As NPOI.SS.UserModel.IFont = WS.Workbook.CreateFont()
                        oFont.FontHeightInPoints = cell.FontHeightInPoints
                        cs.SetFont(oFont)
                    End If

                    ic.CellStyle = cs

                    If cell.Colspan > 1 Then
                        WS.AddMergedRegion(New CellRangeAddress(StartRow, StartRow, C, C + cell.Colspan - 1))
                        C += cell.Colspan - 1
                    End If
                    C += 1
                Next

                StartRow += 1
            Next
        End If
    End Sub


F. 重點講解:
這個 function 在實作時有兩個卡點:
1. 如何合併欄: 
WS.AddMergedRegion(New CellRangeAddress(StartRow, StartRow, C, C + cell.Colspan - 1))

2. 如何設定字型大小和對齊方式:
                    Dim cs As NPOI.SS.UserModel.ICellStyle = WS.Workbook.CreateCellStyle()
                    cs.Alignment = cell.Alignment
                    If cell.FontHeightInPoints > 0 Then
                        Dim oFont As NPOI.SS.UserModel.IFont = WS.Workbook.CreateFont()
                        oFont.FontHeightInPoints = cell.FontHeightInPoints
                        cs.SetFont(oFont)
                    End If

                    ic.CellStyle = cs


這裡有件有有趣的事, 我一開始是這樣寫的.
ic.CellStyle.Alignment = cell.Alignment

結果是整個 WorkSheet 的對齊方式都被改了. 我猜當 WorkSheet 初建立時, CellStyle 都是用同一個. 所以改任一個 cell 的 CellStyle 會同時改到所有 cell 的.

G. 使用方式:
        Dim ltHeader As New List(Of List(Of UW.ExcelPOI.Cell))
        Dim ltLine As New List(Of UW.ExcelPOI.Cell)
        ltLine.Add(New UW.ExcelPOI.Cell(DB.SysConfig.SYSTEM_NAME & "應收明細表", 16,
                                        NPOI.SS.UserModel.HorizontalAlignment.Center, 28))
        ltHeader.Add(ltLine)

        '第二行
        ltLine = New List(Of UW.ExcelPOI.Cell)
        ltLine.Add(New UW.ExcelPOI.Cell("期間: " & Me.txtbl_date_s.Text & " ~ " & Me.txtbl_date_e.Text, 10,
                                        NPOI.SS.UserModel.HorizontalAlignment.Left, 20))
        ltLine.Add(New UW.ExcelPOI.Cell("製表日期: " & Now.ToString("yyyy-MM-dd"), 6,
                                        NPOI.SS.UserModel.HorizontalAlignment.Right, 20))
        ltHeader.Add(ltLine)

        UW.ExcelPOI.DTToExcelAndWriteToClient(newdt, ltHeader:=ltHeader)
More...
Bike, 2017/6/4 下午 07:19:27
Post File With C#
Post 的資料好像會變大, 要改 Web.config
<system.web>
    <httpRuntime requestValidationMode="2.0" maxRequestLength="1024000"/>
</system.web>



程式碼如下:

public string UploadFilesToRemoteUrl(string url, string[] files, NameValueCollection formFields = null)
    {
        string boundary = "----------------------------" + DateTime.Now.Ticks.ToString("x");

        HttpWebRequest request = (HttpWebRequest)WebRequest.Create(url);
        request.ContentType = "multipart/form-data; boundary=" +
                                boundary;
        request.Method = "POST";
        request.KeepAlive = true;

        Stream memStream = new System.IO.MemoryStream();

        var boundarybytes = System.Text.Encoding.ASCII.GetBytes("\r\n--" +
                                                                boundary + "\r\n");
        var endBoundaryBytes = System.Text.Encoding.ASCII.GetBytes("\r\n--" +
                                                                    boundary + "--");


        string formdataTemplate = "\r\n--" + boundary +
                                    "\r\nContent-Disposition: form-data; name=\"{0}\";\r\n\r\n{1}";

        if (formFields != null)
        {
            foreach (string key in formFields.Keys)
            {
                string formitem = string.Format(formdataTemplate, key, formFields[key]);
                byte[] formitembytes = System.Text.Encoding.UTF8.GetBytes(formitem);
                memStream.Write(formitembytes, 0, formitembytes.Length);
            }
        }

        string headerTemplate =
            "Content-Disposition: form-data; name=\"{0}\"; filename=\"{1}\"\r\n" +
            "Content-Type: application/octet-stream\r\n\r\n";

        for (int i = 0; i < files.Length; i++)
        {
            memStream.Write(boundarybytes, 0, boundarybytes.Length);
            var header = string.Format(headerTemplate, "uplTheFile", files[i]);
            var headerbytes = System.Text.Encoding.UTF8.GetBytes(header);

            memStream.Write(headerbytes, 0, headerbytes.Length);

            using (var fileStream = new FileStream(files[i], FileMode.Open, FileAccess.Read))
            {
                var buffer = new byte[1024];
                var bytesRead = 0;
                while ((bytesRead = fileStream.Read(buffer, 0, buffer.Length)) != 0)
                {
                    Response.Write("bytesRead: " + bytesRead.ToString() + "<br>");
                    memStream.Write(buffer, 0, bytesRead);
                }
            }
        }

        memStream.Write(endBoundaryBytes, 0, endBoundaryBytes.Length);
        request.ContentLength = memStream.Length;

        using (Stream requestStream = request.GetRequestStream())
        {
            memStream.Position = 0;
            byte[] tempBuffer = new byte[memStream.Length];
            memStream.Read(tempBuffer, 0, tempBuffer.Length);
            memStream.Close();
            requestStream.Write(tempBuffer, 0, tempBuffer.Length);
        }

        try
        {
            using (var response = request.GetResponse())
            {
                Stream stream2 = response.GetResponseStream();
                StreamReader reader2 = new StreamReader(stream2);
                return reader2.ReadToEnd();
            }
        }
        catch (Exception ex)
        {
            return (ex.ToString());
            throw;
        }
    }
More...
Bike, 2017/1/12 下午 08:21:09
jQuery 之 event.originalEvent
有時候用 jQuery 使用 event 物件時,會發現有些特殊事件的 property 抓不到 (undefined)
例如
mousewheel --> event.wheelDelta 
drop --> event.dataTransfer
touchstart --> event.touches[0].pageX
原因是 jQuery 的 event 只會包裝一般的屬性,特別的屬性要使用 event.originalEvent 去抓
event.originalEvent 是瀏覽器原生的 event

It's also important to note that the event object contains a property called originalEvent, which is the event object that the browser itself created. jQuery wraps this native event object with some useful methods and properties, but in some instances, you'll need to access the original event via event.originalEvent for instance. This is especially useful for touch events on mobile devices and tablets.

所以開發時當有些特殊屬性抓不到時,可以考慮用 event.originalEvent 去抓看看

    // 這是用滾輪放大縮小圖片 (此範例firefox不支援)
    $("#imgProductBig").bind("mousewheel", function (ev) {
        var delta = ev.originalEvent.wheelDelta > 0 ? 1 : -1;
        if (delta > 0 && zoomValue < 150) {
            zoomValue += 10;
        }
        else if (delta < 0 && zoomValue > 50) {
            zoomValue -= 10;
        }
        $(this).css("zoom", zoomValue + '%');
        return false;
    });


 
More...
darren, 2015/4/21 下午 12:03:35
Cached DataTable 要注意的地方

網站開發,善用 Cached DataTable 可以使網站效能倍增,不必一直去資料庫抓資料。
但是使用 Cached DataTable 有一個地方要注意
就是他是 Shared 物件,表示同時有好幾個頁面都可以存取他

例如A網頁將資料抓出,然後變更裡面的DataRow資料,
另一個B網頁也會跟著變更

由於 Cached DataTable 在 Set DataRow Value 時
可能 Critical Section 沒有處理好,若真的同時多個thread 操作
會出現 Exception
(System.ArgumentOutOfRangeException: 索引超出範圍。必須為非負數且小於集合的大小。)

建議:

  • Cached DataTable 最好是只能用來讀,不要Set Value
  • 若需要Set Value,可以使用 DataTable Copy()功能,先複製出來再操作,就不會影響到原始資料

            '這是 UNT FixPage 物件抓取單一資料的範例
            Shared Function GetSpecialPage2FromCachedDT(ByVal Key As Int32) As DB.SpecialPage2
                Dim DT As DataTable = GetAllDataFromBaseTableWithCache()
                Dim Row As DataRow = DT.Rows.Find(Key)
                If Row IsNot Nothing Then
                    '避免每個thread都共用table 寫入資料會出現問題
                    Dim newDT As DataTable = DT.Clone()
                    newDT.ImportRow(Row)
                    Return New SpecialPage2(newDT.Rows(0))
                Else
                    Return Nothing
                End If
            End Function

More...
darren, 2014/9/23 下午 03:34:21
DataTable 的 Rows.Find 效能較佳
因為 SHOPUNT 的線上產品有兩千多筆,然後網站有非常頻繁的查詢
例如檢查產品是否停賣

原本的寫法是用以下方法尋找

DT.Select("Id=" & ProductId) 


後來改寫 DataTable 加上 PrimaryKey

'寫入Cache前先設定好
DT.PrimaryKey = New DataColumn() {obj.Columns("Id")} 
Dim row As DataRow = DT.Rows.Find(ProductId)


共1085筆 找出其中一筆 
Select方法  - 00:00:00.0000559
Rows.Find -   00:00:00.0000064

兩者速度差了約10倍
 
More...
darren, 2013/9/5 上午 11:58:39
|< 12 >|
頁數 1 / 2 下一頁
~ Uwinfo ~