Xtra.Shared
2.2.0
dotnet add package Xtra.Shared --version 2.2.0
NuGet\Install-Package Xtra.Shared -Version 2.2.0
<PackageReference Include="Xtra.Shared" Version="2.2.0" />
<PackageVersion Include="Xtra.Shared" Version="2.2.0" />
<PackageReference Include="Xtra.Shared" />
paket add Xtra.Shared --version 2.2.0
#r "nuget: Xtra.Shared, 2.2.0"
#:package Xtra.Shared@2.2.0
#addin nuget:?package=Xtra.Shared&version=2.2.0
#tool nuget:?package=Xtra.Shared&version=2.2.0
Xtra Shared Library
(v2.2.0)
คุณสมบัติหลัก
- Controllers - Base controller สำหรับ API (
XtraBaseController,XtraBaseAuthenController,XtraBaseMasterController,XtraBaseTransactionController) - Services / DAL - Data access layer ด้วย Dapper รองรับ Oracle และ SQL Server (
XtraBaseDAL,XtraAuthenDAL,XtraTokenDAL,XMasterDAL,XtraTransactionDAL,SysLogDAL,XEmailDAL) - Authentication - JWT Token และ LDAP (
XtraBaseTokenDAL,LDAPHelper) - Email -
SendEmailService,EmailSetting,EmailTemplate - Helpers -
XtraCryptoHelper,XtraConfigurationHelper,AppLogHelper,ExceptionHelper,EmailHelper - Extensions - Extension methods สำหรับ
DataSet,DataTable,JArray,List,object,string,Type,DbType,QueryOptions - Options -
JwtConfigOptions,XtraConfigOptions,XtraConnectionOptions,XtraLogOptions,XtraSmtpOptions
โครงสร้างโปรเจกต์
xtra-shared-library/
Bases/ Parameter และ configuration พื้นฐาน
Controllers/ Base controllers
Extensions/ Extension methods
Helpers/ Utility helpers
Interfaces/ Interfaces ของ DAL และ Service
Models/ Authen, Base, Email
Options/ Strongly-typed options
Services/ DAL และ SendEmailService
scripts/ sonar-scan.ps1 (SonarQube scan ในเครื่อง)
tests/ Unit และ integration tests (Xtra.Shared.Tests, xunit)
อีกโปรเจกต์ในโซลูชัน: xtra-shared-library.tesing-app (แอปสำหรับทดสอบ)
Dependencies หลัก
Dapper, Dapper.Oracle.NetCore, Oracle.ManagedDataAccess.Core, Microsoft.Data.SqlClient, System.IdentityModel.Tokens.Jwt, Microsoft.IdentityModel.Tokens, NETCore.Encrypt, Newtonsoft.Json, System.DirectoryServices.AccountManagement, Serilog.Extensions.Logging, System.Security.Cryptography.Pkcs (pin เวอร์ชันที่แก้ช่องโหว่), Microsoft.AspNetCore.App (FrameworkReference)
คุณภาพโค้ด (SonarQube)
ผล scan ล่าสุด (2026-10-16, v2.2.0) บน SonarQube ในเครื่อง:
| หัวข้อ | ผล |
|---|---|
| Quality Gate | ✅ Passed |
| Bugs / Vulnerabilities / Code smells | 0 / 0 / 0 |
| Reliability / Security / Maintainability | A / A / A |
| Coverage (ทั้งโปรเจกต์) | 76.0% |
| Coverage on New Code | 90.1% |
| Duplication | 3.8% |
Scan เอง: ตั้ง environment variable SONAR_TOKEN (User Token หรือ Global Analysis Token) แล้วรัน
.\scripts\sonar-scan.ps1
Integration tests ใช้ SQL Server LocalDB ((localdb)\MSSQLLocalDB) จึงรันได้เฉพาะ Windows ที่ติดตั้ง LocalDB
บันทึกการเปลี่ยนแปลง
v2.2.0
แก้ข้อค้นพบจาก SonarQube และ bug ที่พบระหว่างเพิ่ม test (test เพิ่มจาก 33 เป็น 324) ต้อง rebuild โปรเจกต์ที่ใช้งาน และควรทดสอบ login/refresh token, การส่งอีเมล, log ลงไฟล์ และไฟล์แนบบน dev ก่อนใช้งานจริง
ความปลอดภัย
XtraBaseController.DeleteFiles: แก้ช่องโหว่ที่ request ส่งFileNameแล้วลบหรือเขียนทับไฟล์ในโฟลเดอร์ของแอปได้ (เช่นappsettings.json) — แนะนำให้ทุกโปรเจกต์อัปเกรดSaveFiles/DeleteFiles/SetDefaultFileและ helper ของโฟลเดอร์ไฟล์แนบ: ปิด path traversal ผ่านDocuType,ID,FileName(เช่น..\..\appsettings.json) — ค่าต้องเป็นชื่อเดี่ยว ไม่มี/\:หรือ..มิฉะนั้นได้ 400; ชื่อไฟล์ที่ upload ถูกตัดเหลือเฉพาะชื่อไฟล์- อ้างอิง
System.Security.Cryptography.Pkcs10.0.13 ตรง เพื่อแทน 9.0.18 ที่ติดมากับMicrosoft.Data.SqlClient/Oracle.ManagedDataAccess.Core(CVE-2026-84008 ระดับ high, CVE-2026-70162 ระดับ moderate) SeparateWordsใช้ Regex ที่มี timeout 1 วินาที (ป้องกัน ReDoS)
Breaking changes
GrantTypes.Password/RefreshToken/ChangeRoleเปลี่ยนจากstaticfield เป็นconstXType.GetOracleDbType/GetOracleMappingTypeมีพารามิเตอร์ใหม่useNameRules(defaulttrue) และผลลัพธ์ของ property แบบ string / nullable เปลี่ยน (ดูหัวข้อแก้ไข)- Member ร่วมของ
AbstractBaseDALและAbstractBaseTokenDALย้ายไปอยู่ใน base class ใหม่AbstractDALCore(ชื่อและ type เหมือนเดิม)
พฤติกรรมที่เปลี่ยน
- JWT claim
iatเป็นตัวเลขวินาที (NumericDate ตาม RFC 7519) แทนข้อความวันที่ตาม culture ของ server — token อ่านได้ด้วยJwtSecurityTokenHandlerแล้ว; token เดิมยังใช้ได้จนหมดอายุ - วันที่ในอีเมล (
EmailHelper.getEmailTemplate) เป็นdd/MM/yyyyแบบ ค.ศ. เสมอ ไม่ขึ้นกับ culture ของ server - ชื่อไฟล์ log เริ่มต้นเป็น
log-yyyyMMdd.txt(เดิมเป็นlog-YYYY{เดือน}DD.txtจาก format ที่ผิด) GetFiles/DeleteFilesจัดการเฉพาะ content folder (ส่วน default folder ถูกปิดไว้ตั้งแต่ปี 2022 และลบโค้ดที่ไม่ทำงานออกแล้ว)- ข้อความของ
DBConcurrencyExceptionใน DAL บางเมธอดเปลี่ยน (เช่นCancelเป็น "cancelling the transaction")
แก้ไข
AppLogHelper.WriteLogFileไม่เคยเขียน log ได้ (error "The parent is missing" ทุกครั้ง) — ตอนนี้เขียนผ่านILoggerหรือลงไฟล์ (มี timestamp นำหน้า) ได้แล้ว และไม่แก้ไข JObject ที่ส่งเข้ามาSendEmailService.SmtpSendAsyncEmailอาจไม่ได้ส่งเมลจริง (ไม่ได้ await แล้ว dispose client) — ตอนนี้ส่งครบทุกฉบับXDataSet.SuggestDuplicateNameวนลูปไม่รู้จบ ทำให้XDataSet.NewInstance/CastJObject/ReplaceTableค้างเมื่อ JSON มี arrayXDataTable.SetValueแบบระบุแถวไม่เคยเซ็ตค่าXDbType.SqlDbTypeNameคืน""เสมอ (เงื่อนไขกลับด้าน) — ตอนนี้คืนชื่อ SQL type เช่นnvarcharXType.GetOracleDbTypeคืนObjectให้ property แบบ string ทุกตัว; กฎตามชื่อ (...ID→ Varchar2,...DATE/...DATETIME→ Date,...TIMESTAMP→ TimeStamp) ไม่เคยทำงาน;int?ได้Object— แก้แล้วทั้งหมดXtraBaseAuthenController.GetJwt(null)throwNullReferenceExceptionแทนการคืน response ว่าง;ClearJwtlog warning แม้ expire สำเร็จExceptionHelper.Clear()throw เมื่อเรียกก่อนเมธอดอื่นEmailHelper: ไม่ตั้งค่าMailToแล้วไม่ throw อีก — ส่งไปที่ผู้รับในข้อมูลอีเมล (ReSendEmailใช้ToEmailของแถว)XtraConfigOptions: property เป็นpublic(เดิมเป็น private ทั้งหมด จึง bind จาก configuration ไม่ได้)XtraQueryOptions.AddQueryData: DTO ที่มี collection / object ซ้อนไม่ throw อีก;Passwordของ DTO ไม่ถูกเก็บ (ตั้งใจ — ระบุชัดในโค้ดแล้ว)XtraBaseTransactionController.GetToken: แจ้ง error ชัดเจนเมื่อไม่ได้ตั้งค่าGetToken/BasicAuthTokenและไม่ block ด้วย.Result
ปรับปรุงโค้ด
- รวมการส่งอีเมลทั้ง 8 จุดไว้ที่
SmtpMailSenderและเพิ่มXtraSmtpOptions(EnableSslยังมาจาก configuration) - DAL ใช้ helper กลาง (
UseStoredProcedure,QueryString,ExecuteInTransaction,QueryInTransaction) — โค้ด DAL ลดลงประมาณ 460 บรรทัด - Structured logging (placeholder มีชื่อ และเช็ค
IsEnabledก่อน serialize),dotnet formatและแก้ analyzer rules (CA/IDE) — issue จาก SonarQube ลดจาก 407 เหลือ 0 .editorconfigจำกัด IDE0290 / IDE0130 / CA1822 / IDE0060 ไว้กับโค้ดที่ไม่ใช่ public (การแก้จะทำให้ public API เปลี่ยน — รอ 3.0.0)
Test และเครื่องมือ
- Unit test 311 ตัว + integration test 13 ตัว บน SQL Server LocalDB (
Category=Integration; GitLab CI ข้ามด้วย--filter "Category!=Integration") - Fake SMTP server ในตัว test (ไม่เพิ่ม package), coverage ผ่าน
coverlet.collector scripts/sonar-scan.ps1สำหรับ scan SonarQube ในเครื่อง (ต้องตั้งSONAR_TOKEN)
ขั้นตอนอัปเกรด
- Rebuild โปรเจกต์ที่ใช้งาน (
GrantTypesเป็นconstและ DAL base class เปลี่ยน) - ถ้ามีโค้ดเรียก
GetOracleDbType/GetOracleMappingTypeกับ property แบบ string ที่ชื่อลงท้ายDate/DateTime/Timestampแต่ค่าไม่ตรงกับ NLS date format ของ Oracle ให้ส่งuseNameRules: false - ถ้ามีระบบที่อ่าน JWT
iatเป็น string ให้แก้เป็นตัวเลข (Unix seconds) - ถ้าแอปใช้
IDหรือDocuTypeที่มี/หรือ\เป็นชื่อโฟลเดอร์ไฟล์แนบ (เช่นPO/2026/001) ต้องเปลี่ยนเป็นค่าที่ไม่มีตัวคั่น path
v2.1.1
- Package ID เปลี่ยนเป็น
Xtra.Shared
v2.1.0
มี breaking changes สำหรับโปรเจกต์ที่สืบทอด base controller หรือใช้ type ของ SqlClient โดยตรง รวมการแก้ของ v2.0.4 ไว้ครบ
Breaking changes
- Constructor ของ base controller รับ logging เพิ่ม: ต้องส่ง
ILogger<T>และIOptions<XtraLogOptions>ให้ base class (XtraBaseController,XtraBaseMasterController,XtraBaseAuthenController,XtraBaseTransactionController) AppLogHelperเป็น static class: เรียกAppLogHelper.Initialize(systemLogDAL, logger, logOptions)ตอน startup แทนการสร้าง instance (เอาConnectionStringและappLogKeyออก)- ย้ายจาก
System.Data.SqlClientไปMicrosoft.Data.SqlClient7.1.1 — โค้ดที่อ้าง namespace เดิมต้องเปลี่ยน - เลิก
throw exเปลี่ยนเป็น throw exception ที่ห่อ inner exception: DAL/token ใช้DBConcurrencyException,XtraQueryOptions.CloneDeepใช้InvalidOperationException, การ cast ผิดใช้InvalidCastException, login ไม่ผ่านใช้UnauthorizedAccessException(เดิมเป็นException) - ถอด
System.Drawing.Commonออกจาก dependencies — โปรเจกต์ที่ใช้ต่อเนื่องผ่านไลบรารีนี้ต้องอ้างเอง - เปลี่ยนจาก package
Microsoft.AspNetCore.*(Authentication.Abstractions, Authorization, Authorization.Policy, Http, Mvc.Core),Microsoft.Net.Http.HeadersและMicrosoft.Extensions.Httpเป็นFrameworkReference Microsoft.AspNetCore.App— โปรเจกต์ที่ใช้ต้องมี ASP.NET Core shared framework
เพิ่ม
XtraLogOptions(Xtra.Options):LogLevel,FileName,Extension,FilePath,IsFileLog,IsDbLog,FileSizeLimitMB,LogRetainDays,RetainFileCountLimit,LogTable,LogColumnMappingAppLogHelper.PrepareLogPath()และGetLogFilePath()อ่านค่าจากXtraLogOptions; เขียน log ผ่านILogger(เพิ่มSerilog.Extensions.Logging)- Config key ใหม่
DefaultFilePathและTempFileExpirationMinutesในXtraKeyConfiguration XtraBaseTransactionController: method ตรวจสิทธิ์ และขอ access token แบบ client credentials; เพิ่ม XML docs ให้ base controllers[SupportedOSPlatform("windows")]บน LDAP helper
แก้ไข
XtraAuthenDAL: ชื่อ stored procedure เริ่มต้นใช้DatabaseTable({table}_Sel_Logout,{table}_Save_Signin, defaultsmUser) เดิมstring.Formatไม่ได้ใช้ชื่อ table- ลบโค้ดที่ comment ไว้และตัวแปรที่ไม่ใช้ใน DAL และ token helpers
ขั้นตอนอัปเกรด
- แก้ constructor ของ controller ที่สืบทอด ให้ส่ง
ILogger<T>และIOptions<XtraLogOptions>และตั้งค่าXtraLogOptionsใน configuration - เรียก
AppLogHelper.Initialize(...)หนึ่งครั้งตอน startup - เปลี่ยน
System.Data.SqlClientเป็นMicrosoft.Data.SqlClient - เพิ่ม
System.Drawing.Commonในโปรเจกต์ถ้าใช้งาน
v2.0.4
แก้ regression ของ v2.0.3 — แนะนำให้ทุกโปรเจกต์ที่ใช้ v2.0.3 ย้ายมา v2.0.4
- คืนพฤติกรรมของ
TitleCaseและCamelCaseให้ตรงกับ v2.0.2:TitleCase(value, removeSpace = false, removeSpecialCharacter = true, lowerRest = false)CamelCase(value, removeSpace = false, removeSpecialCharacter = true, lowerRest = false)
- คืน
RemoveSpecialCharacters(value, removeUnderscore, removeDash, removeSpace)ที่หายไปใน v2.0.3 lowerRest(แปลงเป็นตัวพิมพ์เล็กก่อนเพื่อให้คำตัวพิมพ์ใหญ่ล้วนถูกแปลงด้วย) ยังอยู่ แต่ย้ายไปเป็นพารามิเตอร์ ท้ายสุด และ default เป็นfalse— ถ้าต้องการพฤติกรรมแบบ v2.0.3 ให้ส่งlowerRest: true- เพิ่ม unit tests (
tests/Xtra.Shared.Tests) ล็อกพฤติกรรมของTitleCase/CamelCaseและรันใน GitLab CI - เพิ่ม job
publish_nugetใน GitLab CI (กดรันเอง) สำหรับ publish ขึ้น nuget.org ด้วย Trusted Publishing (ไม่ต้องใช้ API key ถาวร) - Package ID เป็น
CODATIC.XtraPM.Shared.Libraries.NET_10.0(assembly ยังชื่อXtra.Shared, namespaceXtra.Extensions) - ย้าย repository URL เป็น
https://gitlab.com/sharedlibrary/xtra-shared-libraries
v2.0.3 (เลิกใช้ — ห้ามใช้)
- เพิ่ม
CamelCaseและพารามิเตอร์lowerRestให้TitleCaseในXString - อัปเดตแพ็กเกจ dependencies เป็นเวอร์ชันล่าสุด
- ปัญหา: v2.0.3 แตกจาก
masterโดยไม่มีงานของ v2.0.2 ทำให้พารามิเตอร์ตัวที่สองของTitleCase/CamelCaseเปลี่ยนความหมายจากremoveSpecialCharacterเป็นlowerRestโดยไม่มี compile error, ค่า default เปลี่ยน และRemoveSpecialCharactersหายไป ผลคือชื่อที่ได้ต่างจากเดิม เช่นUserIdเป็นuserid,CurrentStatusเป็นcurrentstatus - แก้แล้วใน v2.0.4
v2.0.2
TitleCaseเพิ่มพารามิเตอร์removeSpecialCharacter(defaulttrue)- เพิ่ม
CamelCase(value, removeSpace = false, removeSpecialCharacter = true)และRemoveSpecialCharacters - เพิ่ม
Microsoft.Net.Http.HeadersและถอดMicrosoft.AspNetCore.Authentication.Coreออกจาก dependencies
การใช้งาน
dotnet add package Xtra.Shared --version 2.2.0
Build และ Publish
dotnet build -c Release
dotnet test tests/Xtra.Shared.Tests/Xtra.Shared.Tests.csproj # ทั้งหมด (ต้องมี LocalDB)
dotnet test tests/Xtra.Shared.Tests/Xtra.Shared.Tests.csproj --filter "Category!=Integration" # ไม่รวม integration tests
nuget.exe push {package file} {apikey} -Source
หรือ publish ขึ้น nuget.org ผ่าน GitLab CI: job publish_nuget (กดรันเองบน default branch) ใช้ Trusted Publishing — ต้องตั้ง CI/CD variable NUGET_USERNAME (nuget.org profile name) และมี policy บน nuget.org ที่ตรงกับ project นี้
ดูเพิ่มเติมที่ package-commands.md
ลิงก์
| Product | Versions Compatible and additional computed target framework versions. |
|---|---|
| .NET | net10.0 is compatible. net10.0-android was computed. net10.0-browser was computed. net10.0-ios was computed. net10.0-maccatalyst was computed. net10.0-macos was computed. net10.0-tvos was computed. net10.0-windows was computed. |
-
net10.0
- Dapper (>= 2.1.89)
- Dapper.Oracle.NetCore (>= 1.0.1)
- Microsoft.Data.SqlClient (>= 7.1.1)
- Microsoft.IdentityModel.Tokens (>= 8.23.0)
- NETCore.Encrypt (>= 2.1.1)
- Newtonsoft.Json (>= 13.0.4)
- Oracle.ManagedDataAccess.Core (>= 23.26.301)
- Serilog.Extensions.Logging (>= 10.0.0)
- System.DirectoryServices.AccountManagement (>= 10.0.13)
- System.IdentityModel.Tokens.Jwt (>= 8.23.0)
- System.Security.Cryptography.Pkcs (>= 10.0.13)
NuGet packages
This package is not used by any NuGet packages.
GitHub repositories
This package is not used by any popular GitHub repositories.