diff --git a/Makefile b/Makefile new file mode 100644 index 00000000..2c609879 --- /dev/null +++ b/Makefile @@ -0,0 +1,11 @@ + +MAKE=make +SUBDIRS=Yavsc.Abstract Yavsc + +all: $(SUBDIRS) + +$(SUBDIRS): + $(MAKE) -C $@ + +.PHONY: all $(SUBDIRS) + diff --git a/YaDaemon/TestDaemonStart.cs b/YaDaemon/TestDaemonStart.cs index cb5261b5..e062338d 100644 --- a/YaDaemon/TestDaemonStart.cs +++ b/YaDaemon/TestDaemonStart.cs @@ -1,6 +1,5 @@ namespace YaDaemon { - using YaDaemon; public class TestDaemonStart { diff --git a/Yavsc.Abstract/Makefile b/Yavsc.Abstract/Makefile index 60311884..72f14d69 100644 --- a/Yavsc.Abstract/Makefile +++ b/Yavsc.Abstract/Makefile @@ -1,5 +1,5 @@ CONFIG=Release -VERSION=1.0.5-rc4 +VERSION=1.0.5-rc5 PRJNAME=Yavsc.Abstract PKGFILENAME=$(PRJNAME).$(VERSION).nupkg DESTPATH=. diff --git a/Yavsc.Abstract/Messaging/Topics.cs b/Yavsc.Abstract/Messaging/Topics.cs new file mode 100644 index 00000000..ee0ec9b9 --- /dev/null +++ b/Yavsc.Abstract/Messaging/Topics.cs @@ -0,0 +1,9 @@ +namespace Yavsc.Abstract.Messaging +{ + public static class MessagingConstants { + public static readonly string TopicGeneral = "/topic/general"; + public static readonly string TopicRdvQuery = "/topic/RdvQuery"; + public static readonly string TopicEstimation = "/topic/Estimation"; + public static readonly string TopicHairCutQuery = "/topic/HairCutQuery"; + } +} \ No newline at end of file diff --git a/Yavsc.Abstract/Properties/AssemblyInfo.cs b/Yavsc.Abstract/Properties/AssemblyInfo.cs index 616e1b27..1bde8739 100644 --- a/Yavsc.Abstract/Properties/AssemblyInfo.cs +++ b/Yavsc.Abstract/Properties/AssemblyInfo.cs @@ -25,4 +25,4 @@ using System.Reflection; // by using the '*' as shown below: // [assembly: AssemblyVersion("1.0.*")] [assembly: AssemblyVersion("1.0.5.*")] -[assembly: AssemblyFileVersion("1.0.5.2")] +[assembly: AssemblyFileVersion("1.0.5.3")] diff --git a/Yavsc.Abstract/Workflow/IEvent.cs b/Yavsc.Abstract/Workflow/IEvent.cs index 4e6cf601..8471c1ce 100644 --- a/Yavsc.Abstract/Workflow/IEvent.cs +++ b/Yavsc.Abstract/Workflow/IEvent.cs @@ -11,11 +11,8 @@ namespace Yavsc.Interfaces.Workflow { /// /// string Sender { get; set ; } - /// - /// The message - /// - /// - string Message { get; set; } + + string CreateBody(); } diff --git a/Yavsc.Abstract/Workflow/ILocation.cs b/Yavsc.Abstract/Workflow/ILocation.cs index 926b56bd..797bc9ca 100644 --- a/Yavsc.Abstract/Workflow/ILocation.cs +++ b/Yavsc.Abstract/Workflow/ILocation.cs @@ -1,6 +1,6 @@ namespace Yavsc { - public interface ILocation + public interface ILocation : IPosition { string Address { get; set; } long Id { get; set; } diff --git a/Yavsc.Abstract/Yavsc.Abstract.1.0.5-rc4.nupkg b/Yavsc.Abstract/Yavsc.Abstract.1.0.5-rc4.nupkg index 8e0062fa..03f8a953 100644 Binary files a/Yavsc.Abstract/Yavsc.Abstract.1.0.5-rc4.nupkg and b/Yavsc.Abstract/Yavsc.Abstract.1.0.5-rc4.nupkg differ diff --git a/Yavsc.Abstract/Yavsc.Abstract.1.0.5-rc5.nupkg b/Yavsc.Abstract/Yavsc.Abstract.1.0.5-rc5.nupkg new file mode 100644 index 00000000..dfde01ff Binary files /dev/null and b/Yavsc.Abstract/Yavsc.Abstract.1.0.5-rc5.nupkg differ diff --git a/Yavsc.Abstract/Yavsc.Abstract.nuspec b/Yavsc.Abstract/Yavsc.Abstract.nuspec index feb13a19..3a1af260 100644 --- a/Yavsc.Abstract/Yavsc.Abstract.nuspec +++ b/Yavsc.Abstract/Yavsc.Abstract.nuspec @@ -11,7 +11,7 @@ https://github.com/pazof/yavsc/blob/vnext/Yavsc/wwwroot/images/yavsc.png true - A shared model for a little client/sever app + A shared model for a little client/server app, dealing about establishing some contract, between some human client and provider. diff --git a/Yavsc/ApiControllers/EstimateApiController.cs b/Yavsc/ApiControllers/EstimateApiController.cs index c9f90276..2d16be4b 100644 --- a/Yavsc/ApiControllers/EstimateApiController.cs +++ b/Yavsc/ApiControllers/EstimateApiController.cs @@ -114,14 +114,16 @@ namespace Yavsc.Controllers public IActionResult PostEstimate([FromBody] Estimate estimate) { var uid = User.GetUserId(); - if (!User.IsInRole(Constants.AdminGroupName)) - { + if (estimate.OwnerId==null) estimate.OwnerId = uid; + + if (!User.IsInRole(Constants.AdminGroupName)) { if (uid != estimate.OwnerId) { ModelState.AddModelError("OwnerId","You can only create your own estimates"); return HttpBadRequest(ModelState); } } + if (estimate.CommandId!=null) { var query = _context.RdvQueries.FirstOrDefault(q => q.Id == estimate.CommandId); if (query == null) { diff --git a/Yavsc/Controllers/BlogspotController.cs b/Yavsc/Controllers/BlogspotController.cs index b788bb86..873c1ff7 100644 --- a/Yavsc/Controllers/BlogspotController.cs +++ b/Yavsc/Controllers/BlogspotController.cs @@ -47,23 +47,25 @@ namespace Yavsc.Controllers long[] usercircles = _context.Circle.Include(c=>c.Members).Where(c=>c.Members.Any(m=>m.MemberId == uid)) .Select(c=>c.Id).ToArray(); IQueryable posts ; - if (usercircles != null) { - posts = _context.Blogspot.Include(b => b.Author) + var allposts = _context.Blogspot + .Include(b => b.Author) + .Include(p=>p.ACL) .Include(p=>p.Tags) .Include(p=>p.Comments) - .Include(p=>p.ACL) - .Where(p=> p.AuthorId == uid || p.Visible && - (p.ACL.Count == 0 || p.ACL.Any(a=> usercircles.Contains(a.CircleId)))) - ; + .Where(p=>p.AuthorId == uid || p.Visible); + + if (usercircles != null) { + posts = allposts.Where(p=> p.ACL.Count==0 || p.ACL.Any(a=> usercircles.Contains(a.CircleId))) + ; } else { - posts = _context.Blogspot.Include(b => b.Author) - .Include(p=>p.ACL).Where(p=>p.AuthorId == uid || p.Visible && p.ACL.Count == 0); + posts = allposts.Where(p => p.ACL.Count == 0); } - return View(posts.OrderByDescending( p=> p.DateCreated) - - .GroupBy(p=> p.Title).Skip(skip).Take(maxLen)); + var data = posts.OrderByDescending( p=> p.DateCreated).ToArray(); + var grouped = data.GroupBy(p=> p.Title).Skip(skip).Take(maxLen); + + return View(grouped); } [Route("/Title/{id?}")] diff --git a/Yavsc/Controllers/CommandController.cs b/Yavsc/Controllers/CommandController.cs index 5603c554..d8d20c7a 100644 --- a/Yavsc/Controllers/CommandController.cs +++ b/Yavsc/Controllers/CommandController.cs @@ -174,17 +174,18 @@ namespace Yavsc.Controllers .Devices.Select(d => d.GCMRegistrationId); grep = await _GCMSender.NotifyBookQueryAsync(_googleSettings,regids,yaev); } + // TODO setup a profile choice to allow notifications // both on mailbox and mobile // if (grep==null || grep.success<=0 || grep.failure>0) ViewBag.GooglePayload=grep; - await _emailSender.SendEmailAsync( + ViewBag.EmailSent = await _emailSender.SendEmailAsync( _siteSettings, _smtpSettings, command.PerformerProfile.Performer.UserName, command.PerformerProfile.Performer.Email, $"{command.Client.UserName} (un client) vous demande un rendez-vous", - $"{yaev.Message}\r\n-- \r\n{yaev.Previsional}\r\n{yaev.EventDate}\r\n" + $"{yaev.CreateBody()}\r\n-- \r\n{yaev.Previsional}\r\n{yaev.EventDate}\r\n" ); } ViewBag.Activity = _context.Activities.FirstOrDefault(a=>a.Code == command.ActivityCode); diff --git a/Yavsc/Controllers/GCMDevicesController.cs b/Yavsc/Controllers/GCMDevicesController.cs new file mode 100644 index 00000000..76813e39 --- /dev/null +++ b/Yavsc/Controllers/GCMDevicesController.cs @@ -0,0 +1,78 @@ +using System.Linq; +using System.Security.Claims; +using System.Threading.Tasks; + +using Microsoft.AspNet.Mvc; +using Microsoft.Data.Entity; + + +namespace Yavsc.Controllers +{ + using Models; + using Models.Identity; + + public class GCMDevicesController : Controller + { + private ApplicationDbContext _context; + + public GCMDevicesController(ApplicationDbContext context) + { + _context = context; + } + + // GET: GCMDevices + public async Task Index() + { + var uid = User.GetUserId(); + + var applicationDbContext = _context.GCMDevices.Include(g => g.DeviceOwner).Where(d=>d.DeviceOwnerId == uid); + return View(await applicationDbContext.ToListAsync()); + } + + // GET: GCMDevices/Details/5 + public async Task Details(string id) + { + if (id == null) + { + return HttpNotFound(); + } + + GoogleCloudMobileDeclaration googleCloudMobileDeclaration = await _context.GCMDevices.SingleAsync(m => m.DeviceId == id); + if (googleCloudMobileDeclaration == null) + { + return HttpNotFound(); + } + + return View(googleCloudMobileDeclaration); + } + + // GET: GCMDevices/Delete/5 + [ActionName("Delete")] + public async Task Delete(string id) + { + if (id == null) + { + return HttpNotFound(); + } + + GoogleCloudMobileDeclaration googleCloudMobileDeclaration = await _context.GCMDevices.SingleAsync(m => m.DeviceId == id); + if (googleCloudMobileDeclaration == null) + { + return HttpNotFound(); + } + + return View(googleCloudMobileDeclaration); + } + + // POST: GCMDevices/Delete/5 + [HttpPost, ActionName("Delete")] + [ValidateAntiForgeryToken] + public async Task DeleteConfirmed(string id) + { + GoogleCloudMobileDeclaration googleCloudMobileDeclaration = await _context.GCMDevices.SingleAsync(m => m.DeviceId == id); + _context.GCMDevices.Remove(googleCloudMobileDeclaration); + await _context.SaveChangesAsync(); + return RedirectToAction("Index"); + } + } +} diff --git a/Yavsc/Controllers/Haircut/HairCutCommandController.cs b/Yavsc/Controllers/Haircut/HairCutCommandController.cs index e06378c3..7b14c994 100644 --- a/Yavsc/Controllers/Haircut/HairCutCommandController.cs +++ b/Yavsc/Controllers/Haircut/HairCutCommandController.cs @@ -79,60 +79,30 @@ namespace Yavsc.Controllers ViewData["paymentinfo"] = paymentInfo; command.Regularisation = paymentInfo.DbContent; command.PaymentId = token; - if (paymentInfo != null) - if (paymentInfo.DetailsFromPayPal != null) - if (paymentInfo.DetailsFromPayPal.Ack == AckCodeType.SUCCESS) - if (command.ValidationDate == null) - command.ValidationDate = DateTime.Now; + bool paymentOk = false; + if (paymentInfo.DetailsFromPayPal != null) + if (paymentInfo.DetailsFromPayPal.Ack == AckCodeType.SUCCESS) + { + // FIXME Assert (command.ValidationDate == null) + if (command.ValidationDate == null) { + paymentOk = true; + command.ValidationDate = DateTime.Now; + } + } await _context.SaveChangesAsync(User.GetUserId()); SetViewBagPaymentUrls(id); - if (command.PerformerProfile.AcceptPublicContact) + if (command.PerformerProfile.AcceptPublicContact && paymentOk) { - var invoiceId = paymentInfo.DetailsFromPayPal.GetExpressCheckoutDetailsResponseDetails.InvoiceID; - var payerName = paymentInfo.DetailsFromPayPal.GetExpressCheckoutDetailsResponseDetails.PayerInfo.Address.Name; - var phone = paymentInfo.DetailsFromPayPal.GetExpressCheckoutDetailsResponseDetails.PayerInfo.Address.Phone; - var payerEmail = paymentInfo.DetailsFromPayPal.GetExpressCheckoutDetailsResponseDetails.PayerInfo.Payer; - var amount = string.Join(", ", - paymentInfo.DetailsFromPayPal.GetExpressCheckoutDetailsResponseDetails.PaymentDetails.Select( - p => $"{p.OrderTotal.value} {p.OrderTotal.currencyID}")); - var gender = command.Prestation.Gender; - var date = command.EventDate?.ToString("dd MM yyyy hh:mm"); - var lieu = command.Location.Address; - string clientFinal = (gender == HairCutGenders.Women) ? _localizer["Women"] + - " " + _localizer[command.Prestation.Length.ToString()] : _localizer[gender.ToString()]; MessageWithPayloadResponse grep = null; - var yaev = command.CreateEvent("PaymentConfirmation", - this._localizer["PaymentConfirmation"], - command.Client.GetSender(), -$@"# Paiment confirmé: {amount} - -Effectué par : {payerName} [{payerEmail}] -Identifiant PayPal du paiment: {token} -Identifiant PayPal du payeur: {PayerID} -Identifiant de la facture sur site: {invoiceId} - - -# La prestation concernée: - -Demandeur: {command.Client.UserName} - -Date: {date} - -Lieu: {lieu} - -Le client final: {clientFinal} - -{command.GetBillText()} - -"); - + var yaev = command.CreatePaymentEvent(paymentInfo, _localizer); if (command.PerformerProfile.AcceptNotifications) { if (command.PerformerProfile.Performer.Devices.Count > 0) { var regids = command.PerformerProfile.Performer .Devices.Select(d => d.GCMRegistrationId); - grep = await _GCMSender.NotifyHairCutQueryAsync(_googleSettings, regids, yaev); + + grep = await _GCMSender.NotifyAsync(_googleSettings, regids, yaev); } // TODO setup a profile choice to allow notifications // both on mailbox and mobile @@ -144,8 +114,8 @@ Le client final: {clientFinal} _siteSettings, _smtpSettings, command.PerformerProfile.Performer.UserName, command.PerformerProfile.Performer.Email, - yaev.Reason, - $"{yaev.Message}\r\n-- \r\n{yaev.Previsional}\r\n{yaev.EventDate}\r\n" + yaev.Topic, + yaev.CreateBody() ); } else @@ -321,7 +291,7 @@ Le client final: {clientFinal} DateTime evdate = yaev.EventDate ?? new DateTime(); var result = await _calendarManager.CreateEventAsync(pro.Performer.Id, pro.Performer.DedicatedGoogleCalendar, - evdate, 3600, yaev.Topic, yaev.Message, + evdate, 3600, yaev.Topic, yaev.Client.UserName + " : " + yaev.Reason, yaev.Location?.Address, false ); if (result.Id == null) @@ -333,8 +303,8 @@ Le client final: {clientFinal} _siteSettings, _smtpSettings, pro.Performer.UserName, pro.Performer.Email, - yaev.Reason, - $"{yaev.Message}\r\n-- \r\n{yaev.Previsional}\r\n{yaev.EventDate}\r\n" + $"{yaev.Client.UserName}: {yaev.Reason}", + $"{yaev.Reason}\r\n-- \r\n{yaev.Previsional}\r\n{yaev.EventDate}\r\n" ); } else @@ -456,6 +426,7 @@ Le client final: {clientFinal} bp => bp.UserId == command.PerformerId ); var yaev = command.CreateEvent(_localizer, brSettings); + string msg = yaev.CreateBoby(); MessageWithPayloadResponse grep = null; if (pro.AcceptNotifications @@ -481,7 +452,7 @@ Le client final: {clientFinal} await _calendarManager.CreateEventAsync( pro.Performer.Id, pro.Performer.DedicatedGoogleCalendar, - evdate, 3600, yaev.Topic, yaev.Message, + evdate, 3600, yaev.Topic, msg, yaev.Location?.ToString(), false ); } @@ -491,7 +462,7 @@ Le client final: {clientFinal} command.PerformerProfile.Performer.UserName, command.PerformerProfile.Performer.Email, yaev.Topic + " " + yaev.Sender, - $"{yaev.Message}\r\n-- \r\n{yaev.Previsional}\r\n{yaev.EventDate}\r\n" + $"{msg}\r\n-- \r\n{yaev.Previsional}\r\n{yaev.EventDate}\r\n" ); } ViewBag.Activity = _context.Activities.FirstOrDefault(a => a.Code == command.ActivityCode); diff --git a/Yavsc/Controllers/HomeController.cs b/Yavsc/Controllers/HomeController.cs index 615d710a..03104317 100644 --- a/Yavsc/Controllers/HomeController.cs +++ b/Yavsc/Controllers/HomeController.cs @@ -50,7 +50,7 @@ namespace Yavsc.Controllers } else clicked = DbContext.DimissClicked.Where(d=>d.UserId == uid).Select(d=>d.NotificationId).ToArray(); var notes = DbContext.Notification.Where( - n=> !clicked.Any(c=>n.Id==c) + n=> !clicked.Contains(n.Id) ); this.Notify(notes); ViewData["HaircutCommandCount"] = DbContext.HairCutQueries.Where( diff --git a/Yavsc/Controllers/ManageController.cs b/Yavsc/Controllers/ManageController.cs index dd0ad469..3413ff9d 100644 --- a/Yavsc/Controllers/ManageController.cs +++ b/Yavsc/Controllers/ManageController.cs @@ -122,9 +122,10 @@ namespace Yavsc.Controllers EmailConfirmed = await _userManager.IsEmailConfirmedAsync(user) }; model.HaveProfessionalSettings = _dbContext.Performers.Any(x => x.PerformerId == user.Id); - var usrActs = _dbContext.UserActivities.Include(a=>a.Does).Where(a=> a.UserId == user.Id); + var usrActs = _dbContext.UserActivities.Include(a=>a.Does).Where(a=> a.UserId == user.Id).ToArray(); - model.HaveActivityToConfigure = usrActs.Where( a => ( a.Does.SettingsClassName != null )).Count( a => a.Settings == null)>0; + var usrActToSet = usrActs.Where( a => ( a.Settings == null && a.Does.SettingsClassName != null )).ToArray(); + model.HaveActivityToConfigure = usrActToSet .Count()>0; model.Activity = _dbContext.UserActivities.Include(a=>a.Does).Where(u=>u.UserId == user.Id).ToList(); return View(model); } diff --git a/Yavsc/Helpers/EventHelpers.cs b/Yavsc/Helpers/EventHelpers.cs index a011b066..ccc36795 100644 --- a/Yavsc/Helpers/EventHelpers.cs +++ b/Yavsc/Helpers/EventHelpers.cs @@ -15,12 +15,7 @@ namespace Yavsc.Helpers var yaev = new RdvQueryEvent(subtopic) { Sender = query.ClientId, - Message = string.Format(SR["RdvToPerf"], - query.Client.UserName, - query.EventDate.ToString("dddd dd/MM/yyyy à HH:mm"), - query.Location.Address, - query.ActivityCode)+ - "\n"+query.Reason, + Reason = query.Reason, Client = new ClientProviderInfo {  UserName = query.Client.UserName , UserId = query.ClientId, @@ -46,21 +41,7 @@ namespace Yavsc.Helpers var yaev = query.CreateEvent("NewHairCutQuery", string.Format(Startup.GlobalLocalizer["HairCutQueryValidation"],query.Client.UserName), - $"{query.Client.UserName}", -$@"Un client vient de valider une demande de prestation à votre encontre: - - Prestation: {strprestation} - Client : {query.Client.UserName} - Date: {evdate}, - Adresse: {address} - ------ -{query.AdditionalInfo} - -Facture prévue (non réglée): - -{query.GetBillText()} -") ; + $"{query.Client.UserName}") ; return yaev; } @@ -74,11 +55,7 @@ Facture prévue (non réglée): var yaev = new HairCutQueryEvent("newCommand") { Sender = query.ClientId, - Message = string.Format(SR["RdvToPerf"], - query.Client.UserName, - query.EventDate.ToString("dddd dd/MM/yyyy à HH:mm"), - query.Location.Address, - query.ActivityCode), + Client = new ClientProviderInfo {  UserName = query.Client.UserName , UserId = query.ClientId, diff --git a/Yavsc/Helpers/GoogleHelpers.cs b/Yavsc/Helpers/GoogleHelpers.cs index 54aad5ea..83326a7d 100644 --- a/Yavsc/Helpers/GoogleHelpers.cs +++ b/Yavsc/Helpers/GoogleHelpers.cs @@ -23,67 +23,29 @@ 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.Google.Messaging; - using Models.Messaging; using Models; - using Interfaces.Workflow; - using Yavsc.Models.Calendar; - using Google.Apis.Auth.OAuth2; - using Microsoft.Data.Entity; - using Microsoft.AspNet.Identity.EntityFramework; - using Yavsc.Services; - 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; - - - - + using Models.Calendar; + using Services; /// /// Google helpers. /// public static class GoogleHelpers { - public static async Task NotifyEvent - (this GoogleAuthSettings googleSettings, IEnumerable regids, Event ev) - where Event : IEvent - { - if (ev == null) - throw new Exception("Spécifier un évènement"); - if (ev.Message == null) - throw new Exception("Spécifier un message"); - if (ev.Sender == null) - throw new Exception("Spécifier un expéditeur"); - - if (regids == null) - throw new NotImplementedException("Notify & No GCM reg ids"); - - var msg = new MessageWithPayload() - { - notification = new Notification() - { - title = ev.Topic+" "+ev.Sender, - body = ev.Message, - icon = "icon" - }, - data = ev, - registration_ids = regids.ToArray() - }; - try { - using (var m = new SimpleJsonPostMethod("https://gcm-http.googleapis.com/gcm/send",$"key={googleSettings.ApiKey}")) { - return await m.Invoke(msg); - } - } - catch (Exception ex) { - throw new Exception ("Quelque chose s'est mal passé à l'envoi",ex); - } - } + public static ServiceAccountCredential OupsGetCredentialForApi(IEnumerable scopes) { var initializer = new ServiceAccountCredential.Initializer(Startup.GoogleSettings.Account.client_email); diff --git a/Yavsc/Models/Billing/Estimate.cs b/Yavsc/Models/Billing/Estimate.cs index a159a817..4473b059 100644 --- a/Yavsc/Models/Billing/Estimate.cs +++ b/Yavsc/Models/Billing/Estimate.cs @@ -59,7 +59,6 @@ namespace Yavsc.Models.Billing set { AttachedFiles = value.Split(':').ToList(); } } - [Required] public string OwnerId { get; set; } [ForeignKey("OwnerId"),JsonIgnore] diff --git a/Yavsc/Models/Calendar/ProvidedEvent.cs b/Yavsc/Models/Calendar/ProvidedEvent.cs index 837bdf50..9f061b13 100644 --- a/Yavsc/Models/Calendar/ProvidedEvent.cs +++ b/Yavsc/Models/Calendar/ProvidedEvent.cs @@ -29,12 +29,17 @@ namespace Yavsc.Models.Calendar /// /// Provided event. /// - public class ProvidedEvent : YaEvent { + public class ProvidedEvent : BaseEvent { /// /// The privacy. /// [Required] public Publishing Privacy; - } + + public override string CreateBody() + { + throw new System.NotImplementedException(); + } + } } diff --git a/Yavsc/Models/HairCut/HairCutPaymentEvent.cs b/Yavsc/Models/HairCut/HairCutPaymentEvent.cs new file mode 100644 index 00000000..f6ca7a7e --- /dev/null +++ b/Yavsc/Models/HairCut/HairCutPaymentEvent.cs @@ -0,0 +1,76 @@ +using Microsoft.Extensions.Localization; +using System.Linq; + +using Yavsc.Interfaces.Workflow; +using Yavsc.Models.Haircut; +using Yavsc.ViewModels.PayPal; +using Yavsc.Helpers; + +namespace Yavsc.Models.HairCut +{ + public class HairCutPayementEvent: IEvent + { + public HairCutPayementEvent(string sender, PaymentInfo info, HairCutQuery query, IStringLocalizer localizer) + { + Sender = sender; + this.query = query; + invoiceId = info.DetailsFromPayPal.GetExpressCheckoutDetailsResponseDetails.InvoiceID; + payerName = info.DetailsFromPayPal.GetExpressCheckoutDetailsResponseDetails.PayerInfo.Address.Name; + phone = info.DetailsFromPayPal.GetExpressCheckoutDetailsResponseDetails.PayerInfo.Address.Phone; + payerEmail = info.DetailsFromPayPal.GetExpressCheckoutDetailsResponseDetails.PayerInfo.Payer; + amount = string.Join(", ", + info.DetailsFromPayPal.GetExpressCheckoutDetailsResponseDetails.PaymentDetails.Select( + p => $"{p.OrderTotal.value} {p.OrderTotal.currencyID}")); + gender = query.Prestation.Gender; + date = query.EventDate?.ToString("dd MM yyyy hh:mm"); + lieu = query.Location.Address; + clientFinal = (gender == HairCutGenders.Women) ? localizer["Women"] + + " " + localizer[query.Prestation.Length.ToString()] : localizer[gender.ToString()]; + token = info.DetailsFromPayPal.GetExpressCheckoutDetailsResponseDetails.Token; + payerId = info.DetailsFromPayPal.GetExpressCheckoutDetailsResponseDetails.PayerInfo.PayerID; + } + + public string Topic => "/topic/HaircutPayment"; + + public string Sender { get; set; } + + HairCutQuery query; + + private string invoiceId; + private string payerName; + private string phone; + private string payerEmail; + private string amount; + private HairCutGenders gender; + private string date; + private string lieu; + private string clientFinal; + private string token; + private string payerId; + + public string CreateBody() + { + return $@"# Paiment confirmé: {amount} + +Effectué par : {payerName} [{payerEmail}] +Identifiant PayPal du paiment: {token} +Identifiant PayPal du payeur: {payerId} +Identifiant de la facture sur site: {invoiceId} + + +# La prestation concernée: + +Demandeur: {query.Client.UserName} + +Date: {date} + +Lieu: {lieu} + +Le client final: {clientFinal} + +{query.GetBillText()} + +"; + } + } +} \ No newline at end of file diff --git a/Yavsc/Models/HairCut/HairCutQuery.cs b/Yavsc/Models/HairCut/HairCutQuery.cs index 62871efc..7e7b4aab 100644 --- a/Yavsc/Models/HairCut/HairCutQuery.cs +++ b/Yavsc/Models/HairCut/HairCutQuery.cs @@ -10,6 +10,9 @@ using System.Globalization; using Yavsc.Helpers; using Yavsc.Models.Messaging; using System.Linq; +using Microsoft.Extensions.Localization; +using Yavsc.ViewModels.PayPal; +using Yavsc.Models.HairCut; namespace Yavsc.Models.Haircut { @@ -369,9 +372,15 @@ Prestation.Gender == HairCutGenders.Women ? return bill; } + public HairCutPayementEvent CreatePaymentEvent(PaymentInfo info, IStringLocalizer localizer) + { + + return new HairCutPayementEvent(Client.UserName,info,this, localizer); + } + public virtual BrusherProfile SelectedProfile { get; set; } - public HairCutQueryEvent CreateEvent(string subTopic, string reason, string sender, string message) { + public HairCutQueryEvent CreateEvent(string subTopic, string reason, string sender) { string evdate = EventDate?.ToString("dddd dd/MM/yyyy à HH:mm")??"[pas de date spécifiée]"; string address = Location?.Address??"[pas de lieu spécifié]"; @@ -393,8 +402,7 @@ Prestation.Gender == HairCutGenders.Women ? Id = Id, ActivityCode = ActivityCode, Reason = reason, - Sender = sender, - Message = message + Sender = Client.GetSender() }; return yaev; } diff --git a/Yavsc/Models/HairCut/HairCutQueryEvent.cs b/Yavsc/Models/HairCut/HairCutQueryEvent.cs index e176fbd3..af1c6e2f 100644 --- a/Yavsc/Models/HairCut/HairCutQueryEvent.cs +++ b/Yavsc/Models/HairCut/HairCutQueryEvent.cs @@ -6,14 +6,20 @@ namespace Yavsc.Models.Haircut { public HairCutQueryEvent(string subTopic) { - - Topic = GetType().Name+"/"+subTopic; + Topic = "/topic/HairCutQuery"; + if (subTopic!=null) Topic+="/"+subTopic; } - public string Message + public string CreateBody() { - get; + return $"{Reason}\r\n-- \r\n{Previsional}\r\n{EventDate}\r\n"; + } - set; + public string CreateBoby() + { + return string.Format(Startup.GlobalLocalizer["RdvToPerf"], Client.UserName, + EventDate?.ToString("dddd dd/MM/yyyy à HH:mm"), + Location.Address, + ActivityCode); } public string Sender diff --git a/Yavsc/Models/Messaging/Announce.cs b/Yavsc/Models/Messaging/Announce.cs index 2b17d983..54e8c04c 100644 --- a/Yavsc/Models/Messaging/Announce.cs +++ b/Yavsc/Models/Messaging/Announce.cs @@ -4,7 +4,7 @@ using Yavsc.Interfaces; namespace Yavsc.Models.Messaging { - public enum Reason { + public enum Reason: byte { Private, Corporate, SearchingAPro, @@ -23,6 +23,12 @@ namespace Yavsc.Models.Messaging public string OwnerId { get; set; } [ForeignKey("OwnerId")] - public virtual ApplicationUser Owner { get; set; } + public virtual ApplicationUser Owner { get; set; } + + public string Message { get; set; } + public override string CreateBody() + { + return $"Annonce de {Owner.UserName}: {For}\n\n{Message}"; + } } } \ No newline at end of file diff --git a/Yavsc/Models/Messaging/BaseEvent.cs b/Yavsc/Models/Messaging/BaseEvent.cs index ca78c918..3fd5286f 100644 --- a/Yavsc/Models/Messaging/BaseEvent.cs +++ b/Yavsc/Models/Messaging/BaseEvent.cs @@ -28,7 +28,7 @@ namespace Yavsc.Models.Messaging /// /// Base event. /// - public class BaseEvent : IEvent { + public abstract class BaseEvent : IEvent { public BaseEvent() { Topic = GetType().Name; @@ -39,7 +39,8 @@ namespace Yavsc.Models.Messaging } public string Topic { get; private set; } public string Sender { get; set; } - public string Message { get; set; } + + abstract public string CreateBody(); } diff --git a/Yavsc/Models/Messaging/CircleEvent.cs b/Yavsc/Models/Messaging/CircleEvent.cs index c85b90cd..57374f44 100644 --- a/Yavsc/Models/Messaging/CircleEvent.cs +++ b/Yavsc/Models/Messaging/CircleEvent.cs @@ -28,7 +28,7 @@ namespace Yavsc.Models.Messaging /// /// Event pub. /// - public class CircleEvent: YaEvent + public class CircleEvent: BaseEvent { /// /// Gets or sets the circles. @@ -37,7 +37,12 @@ namespace Yavsc.Models.Messaging [Required(ErrorMessageResourceName="DoSpecifyCircles"), Display(Name="Circles")] public virtual List Circles{ get; set; } - } + + public override string CreateBody() + { + throw new System.NotImplementedException(); + } + } } diff --git a/Yavsc/Models/Messaging/EstimationEvent.cs b/Yavsc/Models/Messaging/EstimationEvent.cs index d856af3e..b846df34 100644 --- a/Yavsc/Models/Messaging/EstimationEvent.cs +++ b/Yavsc/Models/Messaging/EstimationEvent.cs @@ -7,6 +7,7 @@ namespace Yavsc.Models.Messaging using Interfaces.Workflow; using Billing; using Yavsc.Helpers; + using Yavsc.Models.Workflow; public class EstimationEvent: IEvent { @@ -14,7 +15,7 @@ namespace Yavsc.Models.Messaging { Topic = "Estimation"; Estimation = estimate; - var perfer = context.Performers.Include( + perfer = context.Performers.Include( p=>p.Performer ).FirstOrDefault( p => p.PerformerId == estimate.OwnerId @@ -27,12 +28,16 @@ namespace Yavsc.Models.Messaging UserId = perfer.PerformerId }; Sender = perfer.Performer.UserName; - Message = string.Format(SR["EstimationMessageToClient"],perfer.Performer.UserName, - estimate.Title,estimate.Bill.Addition()); + _localizer = SR; } + // TODO via e-mail only: Message = string.Format( + // SR["EstimationMessageToClient"],perfer.Performer.UserName, estimate.Title,estimate.Bill.Addition()); + // ProviderClientInfo ProviderInfo { get; set; } Estimate Estimation { get; set; } + private PerformerProfile perfer; + public string Topic { get; set; @@ -43,9 +48,11 @@ namespace Yavsc.Models.Messaging get; set; } - public string Message + private IStringLocalizer _localizer; + + public string CreateBody() { - get; set; + return string.Format(_localizer["EstimationMessageToClient"], perfer.Performer.UserName, this.Estimation.Bill.Addition()); } } } diff --git a/Yavsc/Models/Messaging/GeneralEvent.cs b/Yavsc/Models/Messaging/GeneralEvent.cs deleted file mode 100644 index a9572d6d..00000000 --- a/Yavsc/Models/Messaging/GeneralEvent.cs +++ /dev/null @@ -1,43 +0,0 @@ -// -// BaseEvent.cs -// -// Author: -// Paul Schneider -// -// 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 . - -using System.ComponentModel.DataAnnotations; - -namespace Yavsc.Models.Messaging -{ -public class GeneralEvent: BaseEvent, ITitle - { - /// - /// The title. - /// - [Required(ErrorMessageResourceName="ChooseATitle")] - [Display(Name="Title")] - public string Title { get; set; } - /// - /// The description. - /// - [Required(ErrorMessageResourceName="ChooseADescription")] - [Display(Name="Description")] - public string Description { get; set; } - - } - -} diff --git a/Yavsc/Models/Messaging/RdvQueryEvent.cs b/Yavsc/Models/Messaging/RdvQueryEvent.cs index 35a27e8f..3158ce4b 100644 --- a/Yavsc/Models/Messaging/RdvQueryEvent.cs +++ b/Yavsc/Models/Messaging/RdvQueryEvent.cs @@ -22,20 +22,19 @@ namespace Yavsc.Models.Messaging { using Interfaces.Workflow; + using Yavsc.Abstract.Messaging; - - -public class RdvQueryEvent: RdvQueryProviderInfo, IEvent + public class RdvQueryEvent: RdvQueryProviderInfo, IEvent { - - public RdvQueryEvent(string subTopic) + public string SubTopic { - Topic = GetType().Name+"/"+subTopic; + get; private set; } - public string Message + public RdvQueryEvent(string subTopic) { - get; set; + Topic = MessagingConstants.TopicRdvQuery; + SubTopic = subTopic; } public string Sender @@ -47,6 +46,14 @@ public class RdvQueryEvent: RdvQueryProviderInfo, IEvent { get; private set; } + + public string CreateBody() + { + return string.Format(Startup.GlobalLocalizer["RdvToPerf"], Client.UserName, + EventDate?.ToString("dddd dd/MM/yyyy à HH:mm"), + Location.Address, + ActivityCode); + } } } diff --git a/Yavsc/Models/Messaging/YaEvent.cs b/Yavsc/Models/Messaging/YaEvent.cs deleted file mode 100644 index ce7304bd..00000000 --- a/Yavsc/Models/Messaging/YaEvent.cs +++ /dev/null @@ -1,48 +0,0 @@ -// -// NFEvent.cs -// -// Author: -// Paul Schneider -// -// Copyright (c) 2015 Paul Schneider -// -// 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 . - -using System.ComponentModel.DataAnnotations; - -namespace Yavsc.Models.Messaging -{ - /// - /// NF event. - /// - public class YaEvent : BaseEvent - { - /// - /// The NF provider identifier. - /// - [Display(Name="From")] - public string FromUserName { get; set; } - - /// - /// The event web page. - /// - [Display(Name="EventWebPage")] - public string EventWebPage { get; set; } - /// - /// The image locator. - /// - [Display(Name="Photo")] - public string Photo { get; set; } - } -} diff --git a/Yavsc/Models/Relationship/Location.cs b/Yavsc/Models/Relationship/Location.cs index 6afa336e..29e8dd7d 100644 --- a/Yavsc/Models/Relationship/Location.cs +++ b/Yavsc/Models/Relationship/Location.cs @@ -7,7 +7,7 @@ namespace Yavsc.Models.Relationship /// /// Position. /// - public class Position + public class Position: IPosition { /// /// The longitude. diff --git a/Yavsc/Resources/Yavsc.Resources.YavscLocalisation.fr.resx b/Yavsc/Resources/Yavsc.Resources.YavscLocalisation.fr.resx index 3968f78f..78d04a37 100644 --- a/Yavsc/Resources/Yavsc.Resources.YavscLocalisation.fr.resx +++ b/Yavsc/Resources/Yavsc.Resources.YavscLocalisation.fr.resx @@ -240,6 +240,7 @@ Nom complet L'envoi du message push a échoué, mais un e-mail a été envoyé Message push envoyé + L'evoi du message Google Cloud a échoué ... Dites en plus, ci àprès, à propos de cet évennement Google n'a pas pu identifier ce lieu Agenda Google @@ -463,5 +464,27 @@ Pour ce faire, suivez le lien suivant : <{1}>. d'au moins {0} et d'au plus {1} caractère(s). Ce champ est d'au plus {0} caractère(s) ({1} en excès). +Un message éléctronique a été envoyé au préstataire. +Un client vient de valider une demande de prestation à votre encontre: + Prestation: {0} + Client : {1} + Date: {2}, + Adresse: {3} + +----- +{4} + +Facture prévue (non réglée): {5} +Un client vient de valider une demande de prestation à votre encontre: + + Prestation: {0} + Client : {1} + Date: {2}, + Adresse: {3} + +----- +{4} + +Facture réglée: {5} diff --git a/Yavsc/Services/IGoogleCloudMessageSender.cs b/Yavsc/Services/IGoogleCloudMessageSender.cs index c6ad796f..f59cab4b 100644 --- a/Yavsc/Services/IGoogleCloudMessageSender.cs +++ b/Yavsc/Services/IGoogleCloudMessageSender.cs @@ -1,6 +1,7 @@ using System.Collections.Generic; using System.Threading.Tasks; +using Yavsc.Interfaces.Workflow; using Yavsc.Models.Google.Messaging; using Yavsc.Models.Haircut; using Yavsc.Models.Messaging; @@ -23,7 +24,9 @@ namespace Yavsc.Services GoogleAuthSettings googlesettings, IEnumerable registrationId, HairCutQueryEvent ev); - - + Task NotifyAsync( + GoogleAuthSettings _googleSettings, + IEnumerable regids, + IEvent yaev); } } diff --git a/Yavsc/Services/MessageServices.cs b/Yavsc/Services/MessageServices.cs index ff3191f7..088a721e 100755 --- a/Yavsc/Services/MessageServices.cs +++ b/Yavsc/Services/MessageServices.cs @@ -11,6 +11,10 @@ using Yavsc.Models; using Yavsc.Models.Google.Messaging; using System.Collections.Generic; using Yavsc.Models.Haircut; +using Yavsc.Interfaces.Workflow; +using System.Linq; +using Microsoft.Extensions.Logging; +using Newtonsoft.Json; namespace Yavsc.Services { @@ -19,6 +23,49 @@ namespace Yavsc.Services // For more details see this link http://go.microsoft.com/fwlink/?LinkID=532713 public class AuthMessageSender : IEmailSender, IGoogleCloudMessageSender { + private ILogger _logger; + + public AuthMessageSender(ILoggerFactory loggerFactory) + { + _logger = loggerFactory.CreateLogger(); + } + public async Task NotifyEvent + ( GoogleAuthSettings googleSettings, IEnumerable regids, Event ev) + where Event : IEvent + { + if (ev == null) + throw new Exception("Spécifier un évènement"); + + if (ev.Sender == null) + throw new Exception("Spécifier un expéditeur"); + + if (regids == null ) + throw new NotImplementedException("Notify & No GCM reg ids"); + var raa = regids.ToArray(); + if (raa.Length<1) + throw new NotImplementedException("No GCM reg ids"); + var msg = new MessageWithPayload() + { + notification = new Notification() + { + title = ev.Topic+" "+ev.Sender, + body = ev.CreateBody(), + icon = "icon" + }, + data = ev, + registration_ids = regids.ToArray() + }; + _logger.LogInformation("Sendding to Google : "+JsonConvert.SerializeObject(msg)); + try { + using (var m = new SimpleJsonPostMethod("https://gcm-http.googleapis.com/gcm/send",$"key={googleSettings.ApiKey}")) { + return await m.Invoke(msg); + } + } + catch (Exception ex) { + throw new Exception ("Quelque chose s'est mal passé à l'envoi",ex); + } + } + /// /// /// @@ -30,18 +77,18 @@ namespace Yavsc.Services /// public async Task NotifyBookQueryAsync(GoogleAuthSettings googleSettings, IEnumerable registrationIds, RdvQueryEvent ev) { - return await googleSettings.NotifyEvent(registrationIds, ev); + return await NotifyEvent(googleSettings,registrationIds, ev); } public async Task NotifyEstimateAsync(GoogleAuthSettings googleSettings, IEnumerable registrationIds, EstimationEvent ev) { - return await googleSettings.NotifyEvent(registrationIds, ev); + return await NotifyEvent(googleSettings,registrationIds, ev); } public async Task NotifyHairCutQueryAsync(GoogleAuthSettings googleSettings, IEnumerable registrationIds, HairCutQueryEvent ev) { - return await googleSettings.NotifyEvent(registrationIds, ev); + return await NotifyEvent(googleSettings, registrationIds, ev); } public Task SendEmailAsync(SiteSettings siteSettings, SmtpSettings smtpSettings, string username, string email, string subject, string message) @@ -78,16 +125,21 @@ namespace Yavsc.Services { throw new NotImplementedException(); } + + public Task NotifyAsync(GoogleAuthSettings _googleSettings, IEnumerable regids, IEvent yaev) + { + throw new NotImplementedException(); + } /* SMS with Twilio: public Task SendSmsAsync(TwilioSettings twilioSettigns, string number, string message) { - var Twilio = new TwilioRestClient(twilioSettigns.AccountSID, twilioSettigns.Token); - var result = Twilio.SendMessage( twilioSettigns.SMSAccountFrom, number, message); - // Status is one of Queued, Sending, Sent, Failed or null if the number is not valid - Trace.TraceInformation(result.Status); - // Twilio doesn't currently have an async API, so return success. +var Twilio = new TwilioRestClient(twilioSettigns.AccountSID, twilioSettigns.Token); +var result = Twilio.SendMessage( twilioSettigns.SMSAccountFrom, number, message); +// Status is one of Queued, Sending, Sent, Failed or null if the number is not valid +Trace.TraceInformation(result.Status); +// Twilio doesn't currently have an async API, so return success. - return Task.FromResult(result.Status != "Failed"); +return Task.FromResult(result.Status != "Failed"); } */ } diff --git a/Yavsc/Startup/Startup.SanityChecks.cs b/Yavsc/Startup/Startup.SanityChecks.cs index 744dfb2f..de80cd71 100644 --- a/Yavsc/Startup/Startup.SanityChecks.cs +++ b/Yavsc/Startup/Startup.SanityChecks.cs @@ -28,19 +28,20 @@ namespace Yavsc var appData = Environment.GetEnvironmentVariable("APPDATA"); if (appData == null) { + logger.LogWarning("AppData was not found in environment variables"); if (SiteSetup.DataDir == null) { SiteSetup.DataDir = "AppData"+env.EnvironmentName; - } else logger.LogWarning("existing setting: "+SiteSetup.DataDir); + logger.LogInformation("Using: "+SiteSetup.DataDir); + } else logger.LogInformation("Using value from settings: "+SiteSetup.DataDir); DirectoryInfo di = new DirectoryInfo(SiteSetup.DataDir); if (!di.Exists) { di.Create(); logger.LogWarning("Created dir : "+di.FullName); - } else logger.LogWarning("existing: "+di.Name); + } else logger.LogInformation("Using existing directory: "+di.Name); SiteSetup.DataDir = Path.Combine(Directory.GetCurrentDirectory(),di.Name); Environment.SetEnvironmentVariable("APPDATA", SiteSetup.DataDir); - logger.LogWarning("AppData was not found in env vars, it has been set to : "+ - Environment.GetEnvironmentVariable("APPDATA")); + logger.LogWarning("It has been set to : "+Environment.GetEnvironmentVariable("APPDATA")); } var creds = GoogleSettings?.Account?.private_key; diff --git a/Yavsc/Views/Command/CommandConfirmation.cshtml b/Yavsc/Views/Command/CommandConfirmation.cshtml index fcb061cf..0d4471f4 100644 --- a/Yavsc/Views/Command/CommandConfirmation.cshtml +++ b/Yavsc/Views/Command/CommandConfirmation.cshtml @@ -22,12 +22,14 @@ if (ViewBag.GooglePayload.failure>0) {

@SR["GCM Notification sending failed"]

- } - else { - +
@Newtonsoft.Json.JsonConvert.SerializeObject(ViewBag.GooglePayload)
} } } + @if (ViewBag.EmailSent) + { +

@SR["EmailSentToPerformer"]

+ } diff --git a/Yavsc/Views/GCMDevices/Delete.cshtml b/Yavsc/Views/GCMDevices/Delete.cshtml new file mode 100644 index 00000000..3720f916 --- /dev/null +++ b/Yavsc/Views/GCMDevices/Delete.cshtml @@ -0,0 +1,52 @@ +@model Yavsc.Models.Identity.GoogleCloudMobileDeclaration + +@{ + ViewData["Title"] = "Delete"; +} + +

Delete

+ +

Are you sure you want to delete this?

+
+

GoogleCloudMobileDeclaration

+
+
+
+ @Html.DisplayNameFor(model => model.DeclarationDate) +
+
+ @Html.DisplayFor(model => model.DeclarationDate) +
+
+ @Html.DisplayNameFor(model => model.GCMRegistrationId) +
+
+ @Html.DisplayFor(model => model.GCMRegistrationId) +
+
+ @Html.DisplayNameFor(model => model.Model) +
+
+ @Html.DisplayFor(model => model.Model) +
+
+ @Html.DisplayNameFor(model => model.Platform) +
+
+ @Html.DisplayFor(model => model.Platform) +
+
+ @Html.DisplayNameFor(model => model.Version) +
+
+ @Html.DisplayFor(model => model.Version) +
+
+ +
+
+ | + Back to List +
+
+
diff --git a/Yavsc/Views/GCMDevices/Details.cshtml b/Yavsc/Views/GCMDevices/Details.cshtml new file mode 100644 index 00000000..3c10cab8 --- /dev/null +++ b/Yavsc/Views/GCMDevices/Details.cshtml @@ -0,0 +1,48 @@ +@model Yavsc.Models.Identity.GoogleCloudMobileDeclaration + +@{ + ViewData["Title"] = "Details"; +} + +

Details

+ +
+

GoogleCloudMobileDeclaration

+
+
+
+ @Html.DisplayNameFor(model => model.DeclarationDate) +
+
+ @Html.DisplayFor(model => model.DeclarationDate) +
+
+ @Html.DisplayNameFor(model => model.GCMRegistrationId) +
+
+ @Html.DisplayFor(model => model.GCMRegistrationId) +
+
+ @Html.DisplayNameFor(model => model.Model) +
+
+ @Html.DisplayFor(model => model.Model) +
+
+ @Html.DisplayNameFor(model => model.Platform) +
+
+ @Html.DisplayFor(model => model.Platform) +
+
+ @Html.DisplayNameFor(model => model.Version) +
+
+ @Html.DisplayFor(model => model.Version) +
+
+
+

+ Edit | + Back to List +

diff --git a/Yavsc/Views/GCMDevices/Index.cshtml b/Yavsc/Views/GCMDevices/Index.cshtml new file mode 100644 index 00000000..425af934 --- /dev/null +++ b/Yavsc/Views/GCMDevices/Index.cshtml @@ -0,0 +1,52 @@ +@model IEnumerable + +@{ + ViewData["Title"] = "Index"; +} + +

Index

+ + + + + + + + + + + +@foreach (var item in Model) { + + + + + + + + +} +
+ @Html.DisplayNameFor(model => model.DeclarationDate) + + @Html.DisplayNameFor(model => model.GCMRegistrationId) + + @Html.DisplayNameFor(model => model.Model) + + @Html.DisplayNameFor(model => model.Platform) + + @Html.DisplayNameFor(model => model.Version) +
+ @Html.DisplayFor(modelItem => item.DeclarationDate) + + @Html.DisplayFor(modelItem => item.GCMRegistrationId) + + @Html.DisplayFor(modelItem => item.Model) + + @Html.DisplayFor(modelItem => item.Platform) + + @Html.DisplayFor(modelItem => item.Version) + + Details | + Delete +
diff --git a/Yavsc/Views/_ViewImports.cshtml b/Yavsc/Views/_ViewImports.cshtml index 20e370f6..f0626605 100755 --- a/Yavsc/Views/_ViewImports.cshtml +++ b/Yavsc/Views/_ViewImports.cshtml @@ -41,6 +41,7 @@ @using Microsoft.Extensions.PlatformAbstractions; @using PayPal.PayPalAPIInterfaceService.Model; + @inject IViewLocalizer LocString @addTagHelper "*, Microsoft.AspNet.Mvc.TagHelpers" @addTagHelper "*, Yavsc" diff --git a/test/UnitTest1.cs b/test/UnitTest1.cs index 0df16748..9f4a9702 100755 --- a/test/UnitTest1.cs +++ b/test/UnitTest1.cs @@ -10,5 +10,24 @@ namespace test1 { } + + + [Fact] + public void PassingTest() + { + Assert.Equal(4, Add(2, 2)); + } + + [Fact] + public void FailingTest() + { + Assert.Equal(5, Add(2, 2)); + } + + int Add(int x, int y) + { + return x + y; + } + } } diff --git a/test/global.json b/test/global.json index 63264e7e..717248e6 100644 --- a/test/global.json +++ b/test/global.json @@ -1,7 +1,7 @@ { - "sdk": { - "version": "2.0.4", - "runtime": "mono", - "architecture": "x64" - } -} + "sdk": { + "version": "2.0.4", + "runtime": "mono", + "architecture": "x64" + } +} \ No newline at end of file diff --git a/test/packages.config b/test/packages.config new file mode 100644 index 00000000..7edb886c --- /dev/null +++ b/test/packages.config @@ -0,0 +1,7 @@ + + + + + + +