files tree made better.

This commit is contained in:
Paul Schneider 2019-01-01 16:28:47 +00:00
commit ccc91bbf19
1630 changed files with 18209 additions and 41860 deletions

View file

@ -0,0 +1,57 @@
// // AnsiToHtmlEncoder.cs
// /*
// paul schneider <paul@pschneider.fr> 19/06/2018 15:58 20182018 6 19
// */
using System.IO;
using System.Diagnostics;
using System.Threading.Tasks;
namespace Yavsc.Helpers
{
public static class AnsiToHtmlEncoder
{
const string DocStart = "<!doctype html>\n<html>\n<head>"+
"<style>body {\ncolor: grey;\nbackground-color: black;\nfont-family:fixed;}\n</style>\n</head>"+
"<body><pre><code>\n";
const string DocEnd = "</code></pre></body></html>";
public static Stream GetStream(StreamReader reader)
{
var procStart = new ProcessStartInfo("node", "node_modules/ansi-to-html/bin/ansi-to-html");
procStart.UseShellExecute = false;
procStart.RedirectStandardInput = true;
procStart.RedirectStandardOutput = true;
// procStart.RedirectStandardError = true;
var mem = new MemoryStream();
var writer = new StreamWriter(mem);
var proc = Process.Start(procStart);
Task.Run(() => {
while (reader.Peek()>-1)
{
proc.StandardInput.WriteLine(reader.ReadLine());
}
proc.StandardInput.Close();
});
writer.WriteLine(DocStart);
while (proc.StandardOutput.Peek()>-1)
{
writer.WriteLine(proc.StandardOutput.ReadLine());
}
writer.WriteLine(DocEnd);
writer.Flush();
mem.Seek(0,SeekOrigin.Begin);
return mem;
}
public static Stream GetStream(Stream inner)
{
var reader = new StreamReader(inner);
return GetStream(reader);
}
}
}

View file

@ -0,0 +1,38 @@
using System;
using System.Linq;
using System.Collections.Generic;
using Microsoft.AspNet.Http;
using Yavsc.ViewModels.Account;
namespace Yavsc.Helpers
{
public static class HttpContextExtensions {
public static IEnumerable<YaAuthenticationDescription> GetExternalProviders(this HttpContext context) {
if (context == null) {
throw new ArgumentNullException(nameof(context));
}
return from description in context.Authentication.GetAuthenticationSchemes()
where !string.IsNullOrEmpty(description.DisplayName)
select
( new YaAuthenticationDescription
{
DisplayName = description.DisplayName,
AuthenticationScheme = description.AuthenticationScheme,
Items = description.Items
});;
}
public static bool IsProviderSupported(this HttpContext context, string provider) {
if (context == null) {
throw new ArgumentNullException(nameof(context));
}
return (from description in context.GetExternalProviders()
where string.Equals(description.AuthenticationScheme, provider, StringComparison.OrdinalIgnoreCase)
select description).Any();
}
}
}

View file

@ -0,0 +1,19 @@
namespace Yavsc.Helpers
{
using Models.Bank;
public static class BankInfoHelpers
{
public static bool IsValid(this BankIdentity info) { 
return ByIbanBIC(info) || ByAccountNumber(info) ;
}
public static bool ByIbanBIC(this BankIdentity info) {
return (info.BIC != null && info.IBAN != null) ;
}
public static bool ByAccountNumber(this BankIdentity info){ 
return (info.BankCode != null && info.WicketCode != null && info.AccountNumber != null && info.BankedKey >0);
}
}
}

View file

@ -0,0 +1,21 @@
using System.Net.Http;
using System.Threading.Tasks;
using Newtonsoft.Json.Linq;
namespace Yavsc.Helpers
{
using Models.societe.com;
public static class ComapnyInfoHelpers { 
public static async Task<CompanyInfoMessage> CheckSiren(this HttpClient web,
string siren, CompanyInfoSettings api)
{
using (var request = new HttpRequestMessage(HttpMethod.Get,
string.Format(Constants.CompanyInfoUrl,siren,api.ApiKey))) {
using (var response = await web.SendAsync(request)) {
var payload = JObject.Parse(await response.Content.ReadAsStringAsync());
return payload.ToObject<CompanyInfoMessage>();
}
}
}
}
}

View file

@ -0,0 +1,72 @@
using System.Collections.Generic;
using Microsoft.AspNet.Mvc;
using Yavsc.Models.Messaging;
namespace Yavsc.Helpers
{
public static class ControllerHelpers
{
public static void NotifyWarning(this Controller controller, string title, string body)
{
var notifs = SetupNotificationList(controller);
notifs.Add(new Notification { title = title, body = body });
}
public static void NotifyInfo(this Controller controller, string title, string body)
{
var notifs = SetupNotificationList(controller);
notifs.Add(new Notification { title = title, body = body });
}
public static void Notify(this Controller controller, IEnumerable<Notification> notes)
{
var notifs = SetupNotificationList(controller);
notifs.AddRange(notes);
}
private static List<Notification> SetupNotificationList(this Controller controller)
{
List<Notification> notifs = (List<Notification>)controller.ViewData["Notify"];
if (notifs == null)
{
controller.ViewData["Notify"] = notifs = new List<Notification>();
}
return notifs;
}
/// <summary>
/// If Json is accepted, serve json,
/// if not, serve a web page.
/// </summary>
/// <param name="controller"></param>
/// <param name="model"></param>
/// <returns></returns>
public static IActionResult ViewOk(this Controller controller, object model)
{
IActionResult result;
if (JsonResponse(controller, model, out result)) return result;
else return controller.View(model);
}
static bool JsonResponse(this Controller controller, object model, out IActionResult result){
if (controller.Request.Headers.Keys.Contains("Accept")) {
var accepted = controller.Request.Headers["Accept"];
if (accepted == "application/json")
{
if (controller.ModelState.ErrorCount>0)
result = controller.HttpBadRequest(controller.ModelState);
else
result = controller.Ok(model);
return true;
}
}
result = null;
return false;
}
public static IActionResult ViewOk(this Controller controller, string viewname, object model = null)
{
IActionResult result;
if (JsonResponse(controller, model, out result)) return result;
else return controller.View(viewname, model);
}
}
}

View file

@ -0,0 +1,78 @@
using Microsoft.Extensions.Localization;
namespace Yavsc.Helpers
{
using Models.Workflow;
using Models.Messaging;
using Yavsc.Models.Haircut;
using Yavsc.Models;
using Yavsc.Models.Billing;
using Yavsc.Abstract.Identity;
public static class EventHelpers
{
public static RdvQueryEvent CreateEvent(this RdvQuery query,
IStringLocalizer SR, string subtopic)
{
var yaev = new RdvQueryEvent(subtopic)
{
Sender = query.ClientId,
Reason = query.Reason,
Client = new ClientProviderInfo { 
UserName = query.Client.UserName ,
UserId = query.ClientId,
Avatar = query.Client.Avatar } ,
Previsional = query.Previsional,
EventDate = query.EventDate,
Location = query.Location,
Id = query.Id,
ActivityCode = query.ActivityCode,
BillingCode = BillingCodes.Rdv
};
return yaev;
}
public static HairCutQueryEvent CreateNewHairCutQueryEvent(this HairCutQuery query,
IStringLocalizer SR)
{
string evdate = query.EventDate?.ToString("dddd dd/MM/yyyy à hh:mm")??"[pas de date spécifiée]";
string address = query.Location?.Address??"[pas de lieu spécifié]";
var p = query.Prestation;
string strprestation = query.Description;
var yaev = query.CreateEvent("NewHairCutQuery",
string.Format(ResourcesHelpers.GlobalLocalizer["HairCutQueryValidation"],query.Client.UserName),
$"{query.Client.Id}");
return yaev;
}
public static string GetSender(this ApplicationUser user)
{
return user.UserName+" ["+user.Id+"@"+Startup.Authority+"]";
}
public static HairCutQueryEvent CreateEvent(this HairMultiCutQuery query,
IStringLocalizer SR, BrusherProfile bpr)
{
var yaev = new HairCutQueryEvent("newCommand")
{
Sender = query.ClientId,
Client = new ClientProviderInfo { 
UserName = query.Client.UserName ,
UserId = query.ClientId,
Avatar = query.Client.Avatar } ,
Previsional = query.Previsional,
EventDate = query.EventDate,
Location = query.Location,
Id = query.Id,
Reason = "Commande groupée!",
ActivityCode = query.ActivityCode,
BillingCode = BillingCodes.MBrush
};
return yaev;
}
}
}

View file

@ -0,0 +1,193 @@
using System;
using System.Drawing;
using System.Drawing.Imaging;
using System.IO;
using System.Net.Mime;
using System.Security.Claims;
using System.Web;
using Microsoft.AspNet.Http;
using Yavsc.Abstract.FileSystem;
using Yavsc.Exceptions;
using Yavsc.Models;
using Yavsc.Models.FileSystem;
using Yavsc.ViewModels;
namespace Yavsc.Helpers
{
public static class FileSystemHelpers
{
public static Func<string,string,long,string>
SignFileNameFormat = new Func<string,string,long,string> ((signType,billingCode,estimateId) => $"sign-{billingCode}-{signType}-{estimateId}.png");
public static FileRecievedInfo ReceiveProSignature(this ClaimsPrincipal user, string billingCode, long estimateId, IFormFile formFile, string signtype)
{
var item = new FileRecievedInfo();
item.FileName = SignFileNameFormat("pro",billingCode,estimateId);
item.MimeType = formFile.ContentDisposition;
var destFileName = Path.Combine(Startup.SiteSetup.Bills, item.FileName);
var fi = new FileInfo(destFileName);
if (fi.Exists) item.Overriden = true;
using (var org = formFile.OpenReadStream())
{
Image i = Image.FromStream(org);
using (Bitmap source = new Bitmap(i))
{
source.Save(destFileName, ImageFormat.Png);
}
}
return item;
}
private static void CreateAvatars(this ApplicationUser user, Bitmap source)
{
var dir = Startup.SiteSetup.Avatars;
var name = user.UserName + ".png";
var smallname = user.UserName + ".s.png";
var xsmallname = user.UserName + ".xs.png";
using (Bitmap newBMP = new Bitmap(source, 128, 128))
{
newBMP.Save(Path.Combine(
dir, name), ImageFormat.Png);
}
using (Bitmap newBMP = new Bitmap(source, 64, 64))
{
newBMP.Save(Path.Combine(
dir, smallname), ImageFormat.Png);
}
using (Bitmap newBMP = new Bitmap(source, 32, 32))
{
newBMP.Save(Path.Combine(
dir, xsmallname), ImageFormat.Png);
}
}
public static string InitPostToFileSystem(
this ClaimsPrincipal user,
string subpath)
{
var root = Path.Combine(AbstractFileSystemHelpers.UserFilesDirName, user.Identity.Name);
var diRoot = new DirectoryInfo(root);
if (!diRoot.Exists) diRoot.Create();
if (!string.IsNullOrWhiteSpace(subpath)) {
if (!subpath.IsValidYavscPath())
{
throw new InvalidPathException();
}
root = Path.Combine(root, subpath);
}
var di = new DirectoryInfo(root);
if (!di.Exists) di.Create();
return di.FullName;
}
public static void DeleteUserFile(this ApplicationUser user, string fileName)
{
var root = Path.Combine(AbstractFileSystemHelpers.UserFilesDirName, user.UserName);
var fi = new FileInfo(Path.Combine(root, fileName));
if (!fi.Exists) return ;
fi.Delete();
user.DiskUsage -= fi.Length;
}
public static FileRecievedInfo ReceiveUserFile(this ApplicationUser user, string root, IFormFile f, string destFileName = null)
{
long usage = user.DiskUsage;
var item = new FileRecievedInfo();
// form-data; name="file"; filename="capt0008.jpg"
ContentDisposition contentDisposition = new ContentDisposition(f.ContentDisposition);
item.FileName = Yavsc.Abstract.FileSystem.AbstractFileSystemHelpers.FilterFileName (destFileName ?? contentDisposition.FileName);
item.MimeType = contentDisposition.DispositionType;
item.DestDir = root;
var fi = new FileInfo(Path.Combine(root, item.FileName));
if (fi.Exists)
{
item.Overriden = true;
usage -= fi.Length;
}
using (var dest = fi.OpenWrite())
{
using (var org = f.OpenReadStream())
{
byte[] buffer = new byte[1024];
long len = org.Length;
if (len > (user.DiskQuota - usage)) {
item.QuotaOffensed = true;
return item;
}
usage += len;
while (len > 0)
{
int blen = len > 1024 ? 1024 : (int)len;
org.Read(buffer, 0, blen);
dest.Write(buffer, 0, blen);
len -= blen;
}
dest.Close();
org.Close();
}
}
user.DiskUsage = usage;
return item;
}
public static HtmlString FileLink(this RemoteFileInfo info, string username, string subpath)
{
return new HtmlString( Startup.UserFilesOptions.RequestPath+"/"+ username +
"/" + (( subpath == null ) ? "" : "/" + subpath ) +
info.Name );
}
public static FileRecievedInfo ReceiveAvatar(this ApplicationUser user, IFormFile formFile)
{
var item = new FileRecievedInfo();
item.FileName = user.UserName + ".png";
var destFileName = Path.Combine(Startup.SiteSetup.Avatars, item.FileName);
var fi = new FileInfo(destFileName);
if (fi.Exists) item.Overriden = true;
Rectangle cropRect = new Rectangle();
using (var org = formFile.OpenReadStream())
{
Image i = Image.FromStream(org);
using (Bitmap source = new Bitmap(i))
{
if (i.Width != i.Height)
{
if (i.Width > i.Height)
{
cropRect.X = (i.Width - i.Height) / 2;
cropRect.Y = 0;
cropRect.Width = i.Height;
cropRect.Height = i.Height;
}
else
{
cropRect.X = 0;
cropRect.Y = (i.Height - i.Width) / 2;
cropRect.Width = i.Width;
cropRect.Height = i.Width;
}
using (var cropped = source.Clone(cropRect, source.PixelFormat))
{
CreateAvatars(user,cropped);
}
}
}
}
item.DestDir = Startup.AvatarsOptions.RequestPath.ToUriComponent();
user.Avatar = $"{item.DestDir}/{item.FileName}";
return item;
}
}
}

View file

@ -0,0 +1,126 @@
//
// GoogleHelpers.cs
//
// Author:
// Paul Schneider <paul@pschneider.fr>
//
// Copyright (c) 2015 GNU GPL
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU Lesser General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU Lesser General Public License for more details.
//
// You should have received a copy of the GNU Lesser General Public License
// along with this program. If not, see <http://www.gnu.org/licenses/>.
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
using Microsoft.Data.Entity;
using Microsoft.AspNet.Identity.EntityFramework;
using Google.Apis.Auth.OAuth2;
using Google.Apis.Services;
using Google.Apis.Compute.v1;
using Google.Apis.Auth.OAuth2.Flows;
using Google.Apis.Util.Store;
using Google.Apis.Auth.OAuth2.Responses;
using Google.Apis.Util;
namespace Yavsc.Helpers
{
using Models;
using Models.Calendar;
using Services;
using Server.Helpers;
/// <summary>
/// Google helpers.
/// </summary>
public static class GoogleHelpers
{
public static async Task<GoogleCredential> GetCredentialForApi(IEnumerable<string> scopes)
{
GoogleCredential credential = await GoogleCredential.GetApplicationDefaultAsync();
var baseClientService = new BaseClientService.Initializer()
{
HttpClientInitializer = credential
};
var compute = new ComputeService(new BaseClientService.Initializer()
{
HttpClientInitializer = credential
});
if (credential.IsCreateScopedRequired)
{
credential = credential.CreateScoped(scopes);
}
return credential;
}
public static async Task<IdentityUserLogin<string>> GetGoogleUserLoginAsync(
this ApplicationDbContext context,
string yavscUserId)
{
var user = context.Users.FirstOrDefaultAsync(u=>u.Id==yavscUserId);
if (user==null) return null;
var googleLogin = await context.UserLogins.FirstOrDefaultAsync(
x => x.UserId == yavscUserId && x.LoginProvider == "Google"
);
return googleLogin;
}
public static async Task<UserCredential> GetGoogleCredential(GoogleAuthSettings googleAuthSettings, IDataStore store, string googleUserLoginKey)
{
if (string.IsNullOrEmpty(googleUserLoginKey))
throw new InvalidOperationException("No Google login");
var flow = new GoogleAuthorizationCodeFlow(new GoogleAuthorizationCodeFlow.Initializer());
var token = await store.GetAsync<TokenResponse>(googleUserLoginKey);
// token != null
var c = SystemClock.Default;
if (token.IsExpired(c)) {
token = await RefreshToken(googleAuthSettings, token);
}
return new UserCredential(flow, googleUserLoginKey, token);
}
public static async Task<Period[]> GetFreeTime (this ICalendarManager manager, string calId, DateTime startDate, DateTime endDate)
{
var evlist = await manager.GetCalendarAsync(calId, startDate, endDate, null) ;
var result = evlist.Items
.Where(
ev => ev.Transparency == "transparent"
)
.Select(
ev => new Period {
Start = ev.Start.DateTime.Value,
End = ev.End.DateTime.Value
}
);
return result.ToArray();
}
public static async Task<TokenResponse> RefreshToken(this GoogleAuthSettings settings, TokenResponse oldResponse)
{
string ep = " https://www.googleapis.com/oauth2/v4/token";
// refresh_token client_id client_secret grant_type=refresh_token
try {
using (var m = new SimpleJsonPostMethod(ep)) {
return await m.Invoke<TokenResponse>(
new { refresh_token= oldResponse.RefreshToken, client_id=Startup.GoogleWebClientConfiguration["web:client_id"],
client_secret=Startup.GoogleWebClientConfiguration["web:client_secret"],
grant_type="refresh_token" }
);
}
}
catch (Exception ex) {
throw new Exception ("No refresh token for Google service account",ex);
}
}
}
}

View file

@ -0,0 +1,60 @@
using System;
using System.Linq;
using System.Threading.Tasks;
using Microsoft.AspNet.Identity.EntityFramework;
using Microsoft.Data.Entity;
using System.Threading;
using Newtonsoft.Json.Linq;
namespace Yavsc.Helpers.Google {
using Yavsc.Models;
using Yavsc.Models.Auth;
public static class GoogleStoreHelper {
public static Task<OAuth2Tokens> GetTokensAsync(this ApplicationDbContext context, string googleUserId)
{
if (string.IsNullOrEmpty(googleUserId))
{
throw new ArgumentException("email MUST have a value");
}
var item = context.Tokens.FirstOrDefault(x => x.UserId == googleUserId);
// TODO Refresh token
return Task.FromResult(item);
}
public static Task StoreTokenAsync(this ApplicationDbContext context, string googleUserId, JObject response, string accessToken,
string tokenType, string refreshToken, string expiresIn
)
{
if (string.IsNullOrEmpty(googleUserId))
{
throw new ArgumentException("googleUserId MUST have a value");
}
var item = context.Tokens.SingleOrDefaultAsync(x => x.UserId == googleUserId).Result;
if (item == null)
{
context.Tokens.Add(new OAuth2Tokens
{
TokenType = "Bearer",
AccessToken = accessToken,
RefreshToken = refreshToken,
Expiration = DateTime.Now.AddSeconds(int.Parse(expiresIn)),
UserId = googleUserId
});
}
else
{
item.AccessToken = accessToken;
item.Expiration = DateTime.Now.AddMinutes(int.Parse(expiresIn));
if (refreshToken != null)
item.RefreshToken = refreshToken;
context.Tokens.Update(item);
}
context.SaveChanges(googleUserId);
return Task.FromResult(0);
}
}
}

View file

@ -0,0 +1,22 @@
using System;
using Microsoft.AspNet.Http;
using Microsoft.AspNet.Mvc.Rendering;
using Yavsc.Models.Drawing;
namespace Yavsc.Helpers
{
public static class HtmlHelpers
{
public static HtmlString Color(this Color c)
{
if (c==null) return new HtmlString("#000");
return new HtmlString(String.Format("#{0:X2}{1:X2}{2:X2}", c.Red, c.Green, c.Blue));
}
public static string ToAbsolute(this HttpRequest request, string url)
{
var host = request.Host;
var isSecure = request.Headers[Constants.SshHeaderKey]=="on";
return (isSecure ? "https" : "http") + $"://{host}/{url}";
}
}
}

View file

@ -0,0 +1,22 @@
using System.Collections.Generic;
using System.Linq;
using Microsoft.AspNet.Mvc.Rendering;
using Yavsc.Models;
using Yavsc.Models.Workflow;
namespace Yavsc.Helpers {
public static class ListItemHelpers {
public static List<SelectListItem> ActivityItems(
this ApplicationDbContext _dbContext, List<UserActivity> activity)
{
List<SelectListItem> items = _dbContext.Activities.Select(
x=> new SelectListItem() {
Value = x.Code, Text = x.Name, Selected = activity.Any(a=>a.DoesCode == x.Code)
} ).ToList();
return items;
}
}
}

View file

@ -0,0 +1,18 @@
using System;
using System.Security.Cryptography;
namespace Yavsc.Helpers {
public class Helper
{
public static string GetHash(string input)
{
HashAlgorithm hashAlgorithm = new SHA256CryptoServiceProvider();
byte[] byteValue = System.Text.Encoding.UTF8.GetBytes(input);
byte[] byteHash = hashAlgorithm.ComputeHash(byteValue);
return Convert.ToBase64String(byteHash);
}
}
}

View file

@ -0,0 +1,52 @@
using System;
using System.Collections.Generic;
using Microsoft.AspNet.Mvc.Rendering;
namespace Yavsc.Server.Helpers
{
public static class PageHelpers
{
public static List<SelectListItem> CreateSelectListItems (this Type enumType, object selectedValue =null)
{
string selectedName = (selectedValue != null) ? enumType.GetEnumName(selectedValue) : null;
var items = new List<SelectListItem> ();
var names = enumType.GetEnumNames();
var values = enumType.GetEnumValues();
for (int index = 0; index < names.Length; index++)
{
var itemName = names[index];
items.Add(new SelectListItem() {
Value = values.GetValue(index).ToString(), Text = itemName, Selected = ( itemName == selectedName)
}) ;
}
var list = new SelectList(items);
return items;
}
public static List<SelectListItem> AddNull(this List<SelectListItem> selectList, string displayNull, object selectedValue = null)
{
selectList.Add(new SelectListItem { Text = displayNull, Value = "", Selected = selectedValue == null });
return selectList;
}
public static List<SelectListItem> CreateSelectListItems<T> (this IEnumerable<T>data,
Func<T,string> dataField,
Func<T,string> displayField = null, object selectedValue =null) where T : class
{
if (displayField == null) displayField = dataField;
var items = new List<SelectListItem> ();
foreach (var dataItem in data)
{
var itemVal = dataField(dataItem);
var itemName = displayField(dataItem);
items.Add(new SelectListItem() {
Value = itemVal, Text = itemName, Selected = ( selectedValue?.Equals(itemVal) ?? false )
}) ;
}
return items;
}
}
}

View file

@ -0,0 +1,174 @@
using System.Collections.Generic;
using Microsoft.Extensions.Logging;
using Yavsc.Models.Billing;
using Microsoft.AspNet.Http;
using System.Threading.Tasks;
using Newtonsoft.Json;
using PayPal.PayPalAPIInterfaceService.Model;
using PayPal.PayPalAPIInterfaceService;
using Yavsc.ViewModels.PayPal;
using Yavsc.Models;
using Microsoft.Data.Entity;
using System.Linq;
using Yavsc.Models.Payment;
namespace Yavsc.Helpers
{
public static class PayPalHelpers
{
private static Dictionary<string,string> payPalProperties = null;
public static Dictionary<string,string> GetPayPalProperties() {
if (payPalProperties==null) {
payPalProperties = new Dictionary<string,string>();
// Don't do:
// payPalProperties.Add("mode", Startup.PayPalSettings.Mode);
// Instead, set the endpoint parameter.
if (Startup.PayPalSettings.Mode == "production") {
// use nvp end point: https://api-3t.paypal.com/nvp
payPalProperties.Add("endpoint", "https://api-3t.paypal.com/nvp");
} else {
payPalProperties.Add("endpoint", "https://api-3t.sandbox.paypal.com/nvp");
}
payPalProperties.Add("clientId", Startup.PayPalSettings.ClientId);
payPalProperties.Add("clientSecret", Startup.PayPalSettings.ClientSecret);
int numClient = 0;
if (Startup.PayPalSettings.Accounts!=null)
foreach (var account in Startup.PayPalSettings.Accounts) {
numClient++;
payPalProperties.Add ($"account{numClient}.apiUsername",account.ApiUsername);
payPalProperties.Add ($"account{numClient}.apiPassword",account.ApiPassword);
payPalProperties.Add ($"account{numClient}.apiSignature",account.Signature);
}
}
return payPalProperties;
}
private static PayPalAPIInterfaceServiceService payPalService = null;
public static PayPalAPIInterfaceServiceService PayPalService {
get {
if (payPalService==null)
payPalService = new PayPal.PayPalAPIInterfaceService.PayPalAPIInterfaceServiceService(GetPayPalProperties());
return payPalService;
}}
public class PaymentUrls
{
public string ReturnUrl { get; set; }
public string CancelUrl { get; set; }
public string CGVUrl { get; set; }
}
public static PaymentUrls GetPaymentUrls(this HttpRequest request, string controllerName, string id)
{
var result = new PaymentUrls
{
ReturnUrl = request.ToAbsolute($"{controllerName}/PaymentConfirmation/{id}"),
CancelUrl = request.ToAbsolute($"{controllerName}/ClientCancel/{id}"),
CGVUrl = request.ToAbsolute($"{controllerName}/CGV")
};
return result;
}
public static SetExpressCheckoutResponseType CreatePayment(this HttpRequest request, string controllerName, NominativeServiceCommand query, string intent = "sale", ILogger logger = null)
{
var items = query.GetBillItems();
var total = items.Addition().ToString("F2");
var coreq = new SetExpressCheckoutReq {};
var urls = request.GetPaymentUrls(controllerName, query.Id.ToString());
var pitem = new PaymentDetailsItemType {};
coreq.SetExpressCheckoutRequest = new SetExpressCheckoutRequestType{
DetailLevel = new List<DetailLevelCodeType?> { DetailLevelCodeType.RETURNALL },
SetExpressCheckoutRequestDetails = new SetExpressCheckoutRequestDetailsType
{
PaymentDetails = new List<PaymentDetailsType>( new [] { new PaymentDetailsType{
OrderDescription = query.Description,
OrderTotal = new BasicAmountType {
currencyID = CurrencyCodeType.EUR,
value = total
},
PaymentDetailsItem = new List <PaymentDetailsItemType> (
items.Select(i => new PaymentDetailsItemType {
Amount = new BasicAmountType { currencyID = CurrencyCodeType.EUR, value = i.UnitaryCost.ToString("F2") },
Name = i.Name,
Quantity = i.Count,
Description = i.Description
})
)
}}),
InvoiceID = query.GetInvoiceId(),
// NOTE don't set OrderDescription : "You cannot pass both the new and deprecated order description.","ErrorCode":"11804
CancelURL = urls.CancelUrl,
ReturnURL = urls.ReturnUrl
}
};
var d = new SetExpressCheckoutRequestDetailsType();
logger.LogInformation($"Creating express checkout for {Startup.PayPalSettings.MerchantAccountUserName} : "+JsonConvert.SerializeObject(coreq));
var response = PayPalService.SetExpressCheckout( coreq, Startup.PayPalSettings.MerchantAccountUserName );
return response;
}
public static async Task<PaymentInfo> GetCheckoutInfo(
this ApplicationDbContext context,
string token)
{
return await CreatePaymentViewModel(context,token,GetExpressCheckoutDetails(token));
}
private static GetExpressCheckoutDetailsResponseType GetExpressCheckoutDetails(string token)
{
GetExpressCheckoutDetailsReq req = new GetExpressCheckoutDetailsReq{
GetExpressCheckoutDetailsRequest = new GetExpressCheckoutDetailsRequestType {
Token = token
}
};
return PayPalService.GetExpressCheckoutDetails(req,Startup.PayPalSettings.Accounts[0].ApiUsername);
}
public static async Task<PaymentInfo> ConfirmPayment(
this ApplicationDbContext context,
string userId,
string payerId,
string token)
{
var details = GetExpressCheckoutDetails(token);
var payment = await context.PayPalPayments.SingleOrDefaultAsync(p=>p.CreationToken == token);
if (payment == null)
{
payment = new PayPalPayment{
ExecutorId = userId,
PaypalPayerId = payerId,
CreationToken = token,
// NOTE: 1 order <=> 1 bill <=> 1 payment
OrderReference = details.GetExpressCheckoutDetailsResponseDetails.InvoiceID,
State = details.Ack.ToString()
};
context.PayPalPayments.Add(payment);
}
else {
payment.ExecutorId = userId;
payment.PaypalPayerId = payerId;
payment.State = details.Ack.ToString();
}
await context.SaveChangesAsync(userId);
// GetCheckoutInfo(,token);
return new PaymentInfo { DbContent = payment, DetailsFromPayPal = details };
}
public static async Task<PaymentInfo> CreatePaymentViewModel (
this ApplicationDbContext context,
string token, GetExpressCheckoutDetailsResponseType fromPayPal)
{
return new PaymentInfo {
DbContent = await context.PayPalPayments
.Include(p=>p.Executor)
.SingleOrDefaultAsync(
p=>p.CreationToken==token),
DetailsFromPayPal = fromPayPal
};
}
}
}

View file

@ -0,0 +1,133 @@
using System.Text.RegularExpressions;
using System.Threading.Tasks;
using MarkdownDeep;
using Microsoft.AspNet.Mvc.Rendering;
using Microsoft.AspNet.Razor.TagHelpers;
namespace Yavsc.Helpers
{
[HtmlTargetElement("div", Attributes = MarkdownContentAttributeName)]
[HtmlTargetElement("h1", Attributes = MarkdownContentAttributeName)]
[HtmlTargetElement("h2", Attributes = MarkdownContentAttributeName)]
[HtmlTargetElement("h3", Attributes = MarkdownContentAttributeName)]
[HtmlTargetElement("p", Attributes = "ismarkdown")]
[HtmlTargetElement("div", Attributes = "ismarkdown")]
[HtmlTargetElement("h1", Attributes = "ismarkdown")]
[HtmlTargetElement("h2", Attributes = "ismarkdown")]
[HtmlTargetElement("h3", Attributes = "ismarkdown")]
[HtmlTargetElement("markdown")]
[OutputElementHint("p")]
public class MarkdownTagHelper : TagHelper
{
private const string MarkdownContentAttributeName = "markdown";
private const string MarkdownMarkAttributeName = "ismarkdown";
[HtmlAttributeName("site")]
public SiteSettings Site { get; set; }
[HtmlAttributeName("base")]
public string Base { get; set; }
[HtmlAttributeName(MarkdownContentAttributeName)]
public string MarkdownContent { get; set; }
static Regex rxExtractLanguage = new Regex("^({{(.+)}}[\r\n])", RegexOptions.Compiled);
private static string FormatCodePrettyPrint(MarkdownDeep.Markdown m, string code)
{
// Try to extract the language from the first line
var match = rxExtractLanguage.Match(code);
string language = null;
if (match.Success)
{
// Save the language
var g = (Group)match.Groups[2];
language = g.ToString();
// Remove the first line
code = code.Substring(match.Groups[1].Length);
}
// If not specified, look for a link definition called "default_syntax" and
// grab the language from its title
if (language == null)
{
var d = m.GetLinkDefinition("default_syntax");
if (d != null)
language = d.title;
}
// Common replacements
if (language == "C#")
language = "csharp";
if (language == "C++")
language = "cpp";
// Wrap code in pre/code tags and add PrettyPrint attributes if necessary
if (string.IsNullOrEmpty(language))
return string.Format("<pre><code>{0}</code></pre>\n", code);
else
return string.Format("<pre class=\"prettyprint lang-{0}\"><code>{1}</code></pre>\n",
language.ToLowerInvariant(), code);
}
/// <summary>
/// Transforms a string of Markdown into HTML.
/// </summary>
/// <param name="text">The Markdown that should be transformed.</param>
/// <param name="urlBaseLocation">The url Base Location.</param>
/// <returns>The HTML representation of the supplied Markdown.</returns>
public string Markdown(string text, string urlBaseLocation = "")
{
// Transform the supplied text (Markdown) into HTML.
var markdownTransformer = GetMarkdownTransformer();
markdownTransformer.UrlBaseLocation = urlBaseLocation;
string html = markdownTransformer.Transform(text);
// Wrap the html in an MvcHtmlString otherwise it'll be HtmlEncoded and displayed to the user as HTML :(
return html;
}
internal Markdown GetMarkdownTransformer()
{
var markdownTransformer = new Markdown();
markdownTransformer.ExtraMode = true;
markdownTransformer.NoFollowLinks = true;
markdownTransformer.SafeMode = false;
markdownTransformer.FormatCodeBlock = FormatCodePrettyPrint;
markdownTransformer.ExtractHeadBlocks = true;
markdownTransformer.UserBreaks = true;
return markdownTransformer;
}
public ModelExpression Content { get; set; }
public async override Task ProcessAsync(TagHelperContext context, TagHelperOutput output)
{
if (output.TagName == "markdown")
{
output.TagName = null;
}
output.Attributes.RemoveAll("markdown");
var content = await GetContent(output);
var markdown = content;
var htbase = Base;
var html = Markdown(markdown, htbase);
output.Content.SetHtmlContent(html ?? "");
}
private async Task<string> GetContent(TagHelperOutput output)
{
if (MarkdownContent != null)
return MarkdownContent;
if (Content != null)
return Content.Model?.ToString();
return (await output.GetChildContentAsync(false)).GetContent();
}
}
}

View file

@ -0,0 +1,200 @@
using System;
using System.Diagnostics;
using System.IO;
using System.Linq;
using Microsoft.AspNet.Http;
using Microsoft.AspNet.Mvc;
using Microsoft.AspNet.Mvc.Rendering;
using Microsoft.AspNet.Mvc.ViewEngines;
namespace Yavsc.Helpers
{
using ViewModels.Gen;
public class TeXString : HtmlString
{
public TeXString(TeXString teXString): base(teXString.ToString())
{
}
public TeXString(string str) : base(str)
{
}
public static TeXString operator+ (TeXString a, TeXString b) {
return new TeXString(a.ToString()+b.ToString());
}
}
public class Replacement
{
string target;
string replacement;
public Replacement(string target, string replacement)
{
this.target = target;
this.replacement = replacement;
}
public string Execute(string source)
{
return source?.Replace(target, replacement) ?? null;
}
}
public static class TeXHelpers
{
public static readonly Replacement[] SpecialCharsDefaultRendering =
{
new Replacement("<","\\textless"),
new Replacement(">","\\textgreater"),
new Replacement("©","\\copyright"),
new Replacement("®","\\textregistered"),
new Replacement("\\","\\textbackslash"),
new Replacement("™","\\texttrademark"),
new Replacement("¶","\\P"),
new Replacement("|","\\textbar"),
new Replacement("%","\\%"),
new Replacement("{","\\{"),
new Replacement("}","\\}"),
new Replacement("_","\\_"),
new Replacement("#","\\#"),
new Replacement("$","\\$"),
new Replacement("_","\\_"),
new Replacement("¿","\\textquestiondown"),
new Replacement("§","\\S"),
new Replacement("£","\\pounds"),
new Replacement("&","\\&"),
new Replacement("¡","\\textexclamdown"),
new Replacement("†","\\dag"),
new Replacement("","\\textendash"),
new Replacement("°","\\textdegree")
};
public static TeXString ToTeX(this string source, string defaultValue="\\textit{néant}")
{
if (source==null) return new TeXString(defaultValue);
string result=source;
foreach (var r in SpecialCharsDefaultRendering)
{
result = r.Execute(result);
}
return new TeXString(result);
}
public static TeXString ToTeXCell(this string source, string defaultValue="\\textit{néant}")
{
if (source==null) return new TeXString(defaultValue);
string result=source;
foreach (var r in SpecialCharsDefaultRendering)
{
result = r.Execute(result);
}
result = result.Replace("\n","\\tabularnewline ");
return new TeXString(result);
}
public static string NewLinesWith(this string target, string separator)
{
var items = target.Split(new char[] { '\n' }).Where(
s => !string.IsNullOrWhiteSpace(s));
return string.Join(separator, items);
}
public static TeXString ToTeXLines(this string source, string defaultValue, string lineSeparator = "\n\\\\")
{
if (source == null) return new TeXString(defaultValue);
return new TeXString( source.ToTeX().ToString().NewLinesWith(lineSeparator) );
}
public static TeXString SplitAddressToTeX (this string source, string lineSeparator = "\n\\\\", string defaultValue = "\\textit{pas d'adresse postale}")
{
if (string.IsNullOrWhiteSpace(source)) return new TeXString(defaultValue);
var alines = source.Split(',');
var texlines = alines.Select(l=>l.ToTeX().ToString());
return new TeXString(string.Join(lineSeparator,texlines));
}
public static bool GenerateEstimatePdf(this PdfGenerationViewModel Model)
{
string errorMsg = null;
var billdir = Model.DestDir;
var tempdir = Startup.SiteSetup.TempDir;
string name = Model.BaseFileName;
string fullname = new FileInfo(
System.IO.Path.Combine(tempdir, name)).FullName;
string ofullname = new FileInfo(
System.IO.Path.Combine(billdir, name)).FullName;
FileInfo fi = new FileInfo(fullname + ".tex");
FileInfo fo = new FileInfo(ofullname + ".pdf");
using (StreamWriter sw = new StreamWriter(fi.FullName))
{
sw.Write(Model.TeXSource);
}
if (!fi.Exists)
{
errorMsg = "Source write failed";
}
else
{
using (Process p = new Process())
{
p.StartInfo.WorkingDirectory = tempdir;
p.StartInfo = new ProcessStartInfo();
p.StartInfo.UseShellExecute = false;
p.StartInfo.WorkingDirectory = tempdir;
p.StartInfo.FileName = "/usr/bin/texi2pdf";
p.StartInfo.Arguments = $"--batch --build-dir=. -o {fo.FullName} {fi.FullName}";
p.Start();
p.WaitForExit();
if (p.ExitCode != 0)
{
errorMsg = $"Pdf generation failed with exit code: {p.ExitCode}";
}
else
{
fi.Delete();
var di = new DirectoryInfo(Path.Combine(tempdir,$"{Model.BaseFileName}.t2d"));
di.Delete(true);
}
}
}
Model.Generated = fo.Exists;
Model.GenerationErrorMessage = new HtmlString(errorMsg);
return fo.Exists;
}
public static string RenderViewToString(
this Controller controller, IViewEngine engine,
IHttpContextAccessor httpContextAccessor,
string viewName, object model)
{
using (var sw = new StringWriter())
{
if (engine == null)
throw new InvalidOperationException("no engine");
// try to find the specified view
controller.TryValidateModel(model);
ViewEngineResult viewResult = engine.FindPartialView(controller.ActionContext, viewName);
// create the associated context
ViewContext viewContext = new ViewContext();
viewContext.ActionDescriptor = controller.ActionContext.ActionDescriptor;
viewContext.HttpContext = controller.ActionContext.HttpContext;
viewContext.TempData = controller.TempData;
viewContext.View = viewResult.View;
viewContext.Writer = sw;
// write the render view with the given context to the stringwriter
viewResult.View.RenderAsync(viewContext);
viewResult.EnsureSuccessful();
return sw.GetStringBuilder().ToString();
}
}
}
}

View file

@ -0,0 +1,47 @@
using System.Collections.Generic;
using System.Linq;
using Microsoft.Data.Entity;
using Yavsc.Models;
using Yavsc.Models.Blog;
namespace Yavsc.Helpers
{
public static class UserHelpers
{
/// <summary>
/// The avatar ...
/// </summary>
/// <param name="dbContext"></param>
/// <param name="userId"></param>
/// <param name="imgFmt"></param>
/// <returns></returns>
// FIXME support imgFmt
public static string AvatarUri(this ApplicationDbContext dbContext, string userId, string imgFmt )
{
var user = dbContext.Users.FirstOrDefault(u => u.Id == userId);
if (user==null) return Constants.AnonAvatar;
if (user.Avatar==null) return Constants.DefaultAvatar;
var avatar = user.UserName;
return $"/Avatars/{avatar}{imgFmt}.png";
}
public static IEnumerable<BlogPost> UserPosts(this ApplicationDbContext dbContext, string posterId, string readerId)
{
long[] readerCirclesMemberships = dbContext.Circle.Include(c=>c.Members).Where(c=>c.Members.Any(m=>m.MemberId == readerId))
.Select(c=>c.Id).ToArray();
var result = (readerId!=null)
?
dbContext.Blogspot.Include(
b => b.Author
).Include(p=>p.ACL).Where(x => x.Author.Id == posterId &&
(x.Visible &&
(x.ACL.Count==0 || x.ACL.Any(a=> readerCirclesMemberships.Contains(a.CircleId)))))
:
dbContext.Blogspot.Include(
b => b.Author
).Where(x => x.Author.Id == posterId && x.Visible);
// BlogIndexKey
return result.OrderByDescending(p => p.DateCreated);
}
}
}

View file

@ -0,0 +1,38 @@
namespace Yavsc.Helpers
{
using System.Collections.Generic;
using System.Linq;
using Microsoft.Data.Entity;
using Yavsc.Models;
using Yavsc.Services;
using Yavsc.ViewModels.FrontOffice;
public static class WorkflowHelpers
{
public static List<PerformerProfileViewModel> ListPerformers(this ApplicationDbContext context,
IBillingService billing,
string actCode)
{
var settings = billing.GetPerformersSettingsAsync(actCode).Result?.ToArray();
var actors = context.Performers
.Include(p=>p.Activity)
.Include(p=>p.Performer)
.Include(p=>p.Performer.Posts)
.Include(p=>p.Performer.Devices)
.Where(p => p.Active && p.Activity.Any(u=>u.DoesCode==actCode)).OrderBy( x => x.Rate )
.ToArray();
List<PerformerProfileViewModel> result = new List<PerformerProfileViewModel> ();
foreach (var perfer in actors)
{
var view = new PerformerProfileViewModel(perfer, actCode, settings?.FirstOrDefault(s => s.UserId == perfer.PerformerId));
result.Add(view);
}
return result;
}
}
}