• Как сохранить IP-адрес клиента при подключении по OpenVPN?

    @Drno
    Да. Надо убрать в конфиге клиента строку «шлюз в впн»
    Нагуглите, по памяти не помню как это в конфиге указывается
    Ответ написан
    4 комментария
  • Как правильно открыть доступ к ресурсам в локальной сети пользователям через VPN?

    @AlexVWill
    Необходимо, чтобы доступ к Gitlab осуществлялся по доменному имени git.example.ru, но только после подключения по VPN.

    1) В DNS регистратора доменных имен прописываешь IP сервера, на котором будет хостится git.example.ru
    2) В вируальном хостинге Apache прописывешь доступ к git.example.ru только из подсети VPN
    Как это сделать читай подробнее вот тут в разделе 4.
    Ответ написан
    1 комментарий
  • Как правильно интегрировать несколько систем в компании?

    vabka
    @vabka Куратор тега C#
    Токсичный шарпист
    Все варианты по своему допустимы и "правильного" пути тут нет.
    1. Проблема может возникнуть, если БД системы изменится или понадобится какая-нибудь дополнительная валидация
    2. Вроде ок, но нужно добавлять и поддерживать методы в каждой API-шке, и следить за совместимостью
    3. Дополнительное звено в инфраструктуре. Придётся потратиться на развёртывание и поддержку, ну и заплатить задержками.

    Я бы выбрал вариант с API тк он кажется самым адекватным в соотношении цена/качество.
    Ответ написан
    Комментировать
  • Как правильно интегрировать несколько систем в компании?

    Jeer
    @Jeer
    уверенный пользователь
    Привет,
    Проблема существует практически на всех предприятиях, но обычно это разные системы, типа 1с на кадры, самописная c# по документам и какая-нибудь готовая опен-сорц система поддержки на php. Ваш вариант, что всё написано на одной технологии благо, используйте это, заворачивайте в нугет библиотеки.
    Про esb - все очереди используются для синхронизации данных. То есть, у вас изменился некий сотрудник в кадрах, сохраняется не напрямую в бд, а через очередь. Другие системы так же подписаны на эту очередь и обновление сущности сотрудника идёт во всех системах, которые хранят дубли необходимых им данных. Как вы понимаете, тут куча накладных расходов и нештатных ситуаций. За этим нужно следить и как-то восстанавливать/докачивать данные. Тем не менее, это самый правильный вариант, ибо в противном случае синхронизацию данных делают кастылями через вьюхи/джобы/хранимки и как только отвратительно не делают. В общем, если хватает скиллов - делайте так, будут независимые рабочие приложения.
    По общению через апи - там нет проблем с какими-то маленькими и атомарными операциями. Проблемы начинаются когда необходимы _распределённые транзакции_ погуглите про это, как реализовывают и оцените насколько тяжелее будет разработка. Вторая тут проблема - это отчёты, тупо джоины. Вам нужно выгрузить какую-то консолидированную инфу из одной системы, вы делаете, но в ней у вас только айдишники пользователей. Либо вы эти айдишники отправляете в сервис кадров и получаете развёрную инфу по каждому, либо на каждый такой запрос вообще грузите полный список пользователей. А потом ещё говорят, нужно исключить данные по пользователям на время их отсутствия. Опять же эти данные в сервисе кадров и, в общем, нужно лепить какой-то большой снежный ком не из снега. Окей, если прям вопрос с отчётами, можно будет заводить какие-то консолидированные хранилища и все системы будут туда сливать данные, но вот при обычном использовании вам всё равно потребуется делать большие джоины, какие с этим косяки я примерно описал.
    По варианту общих сервисов, я за него из-за простоты:
    Хранить строки подключений нужно в каждом проекте - это не проблема
    Дублировать бизнес-логику не нужно, выносите её так же в общие сервисы
    Обновлять будет нужно оба сервера, если в общем сервисе баг. Тут разговор, очевидно, про "баг на проде" - из-за общего кода будет баг на обоих продакшенах. Окей, как часто у вас возникают такие ситуации и насколько долго обновить два прода вместо одного?
    Ответ написан
    1 комментарий
  • Как правильно создавать NuGet-пакеты в Solution с большим количеством проектов?

    @rare
    А вы предполагаете использовать project2, project3 недависимо от project1? Если да, то собирать их отдельно в виде пакетов, потом подключать. Если нет, то может вам сначала собрать всё в одну либу с помощью ilmerge, а потом ее упаковать в .nupkg. Например, consul так собирается.
    https://github.com/PlayFab/consuldotnet/blob/maste...
    Ответ написан
    3 комментария
  • C#: Реализация UnitOfWork factory?

    1) https://habrahabr.ru/post/321050/
    2) https://habrahabr.ru/post/276593/
    3) Посмотреть примеры кода на https://code.msdn.microsoft.com/
    - Unit of Work & Repositories Framework
    - KiksApp Enterprise application architecture Onion
    4) Pluralsight
    - Become a Full-stack .NET Developer - Advanced Topics
    - Become a Full-stack .NET Developer - Architecture and Testing
    - Become a Full-stack .NET Developer - Fundamentals
    Ответ написан
    1 комментарий
  • Когда нужно получать роли пользователя ASP.NET MVC?

    В Identity 2.0 вроде по умолчанию каждые 30 минут куки обновляется, мол изменился пароль или еще чего проверяет, так же и роли обновляет.
    Изменить на меньшее время.
    Caching Role Information

    // Enable the application to use a cookie to store information for the signed in user
                // and to use a cookie to temporarily store information about a user logging in with a third party login provider
                // Configure the sign in cookie
                app.UseCookieAuthentication(new CookieAuthenticationOptions
                {
                    AuthenticationType = DefaultAuthenticationTypes.ApplicationCookie,
                    LoginPath = new PathString("/Account/Login"),
                    Provider = new CookieAuthenticationProvider
                    {
                        // Enables the application to validate the security stamp when the user logs in.
                        // This is a security feature which is used when you change a password or add an external login to your account.  
                        OnValidateIdentity = SecurityStampValidator.OnValidateIdentity<ApplicationUserManager, ApplicationUser>(
                            validateInterval: TimeSpan.FromMinutes(30),
                            regenerateIdentity: (manager, user) => user.GenerateUserIdentityAsync(manager))
                    }
                });
    Ответ написан
    2 комментария
  • Как правильно добавить свои свойства в custom IIdentity ASP.NET (OWIN)?

    @dmitryKovalskiy
    программист средней руки
    По первому вопросу есть решение следующее(костыльное на мой взгляд, но бывало и хуже) - унаследоваться от BaseController и создать свой BaseController. В него можно добавить свойство CurrentUser(например), возвращающее ваш класс реализующий и расширяющий IPrincipal. А свойство в свою очередь должно быть реализовано как приведение User c типом IPrincipal к вашему классу.
    Ответ написан
    5 комментариев
  • C#: Как рекурсивно наследовать свойства класса?

    yarosroman
    @yarosroman Куратор тега C#
    C# the best
    Модификатор new вам в помощь

    public abstract class BaseItem
        {
            public int Id { get; set; }
            public string Title { get; set; }
            public virtual IEnumerable<BaseItem> Childs { get; set; }
    
            public BaseItem()
            {
                Childs = new List<BaseItem>();
            }
        }
    
        public class Item : BaseItem
        {
            public new IEnumerable<Item> Childs { get; set; }
        }
    Ответ написан
    2 комментария
  • Как реализовать сервис обработки очереди на C# + EF 6?

    Neuroware
    @Neuroware
    Программист в свободное от работы время
    есть приложение с примерно такой же архитектурой, только сам "файл" в моем случае кладу туда же в базу, чтобы сервис не зависел от какой бы то ни было папки. Вопросов по надежности и скорострельности нет совсем, все работает очень шустро. Параллельную обработку сделал следующим путем:
    • В таблицу добавил еще одно поле "№обработчика"
    • Приложение обработчик создает N отдельных потоков, каждый изначально имеет определенный ID
    • Поток делает Update первой записи из таблицы, у которой "№обработчика" is null
    • Делает селект в базу выбирая записи у которых № обработчика тот же что и ID потока
    • Обрабатывает их и обновляет статус.


    Таким образом получается, что потоки "отбирают" себе по задаче, обрабатывают ее и обновляют статус и так по кругу.
    Ответ написан
    3 комментария
  • Можно ли реализовать следущий подход с помощью Generic типов?

    Nipheris
    @Nipheris Куратор тега C#
    interface IFoo
    {
      // Не содержит метод Commit()
      // Но содержит все остальные методы и свойства, которые реализованы в классе Foo
    }
    interface ITransaction
    {
        void Commit();
    }
    class Foo : IFoo, ITransaction
    {
      // ...
      
      public void Commit() 
      {
        // ...
      }
    }

    class Bar<T, TImpl> where TImpl : T, ITransaction, new()
    {
      private readonly TImpl _foo;
    
      protected T Foo {
        get { return _foo; }
      }
    
      public Bar() {
        _foo = new TImpl();
      }
     
      public void Commit()
      {
        _foo.Commit();
      }
    }
    Ответ написан
    3 комментария
  • ASP.NET Custom Authentication Service + OWIN или ASP.NET Identity 2.0?

    artem_b89
    @artem_b89
    Сетевой бездельник
    1) Достаточно
    2) В Identity реализован базовый функционал работы с пользователями/ролями и т.д., возможность подключения авторизации через стороннии сервисы.
    Если нужна простейшая аутентификация/авторизация, то Identity в целом не нужен, достаточно будет найти в DAL пользователя с указанными логином и паролем и авторизовать его.
    Псевдокод:
    public User Validate(string login, string secret)
    {
      return DbContext.Users.FirstOrDefault(x=>x.login == login && secret == secret );
    }  
    public async void SignIn(User user)
    {
    	List<Claim> claims = new List<Claim>();	
    	claims.Add(new Claim(ClaimTypes.Name, user.Name));
    	ClaimsIdentity identity = new ClaimsIdentity(claims, CookieAuthenticationDefaults.AuthenticationScheme);
    	ClaimsPrincipal principal = new ClaimsPrincipal(identity);
    	await HttpContext.Authentication.SignInAsync(CookieAuthenticationDefaults.AuthenticationScheme, principal);
    }
    public async void SignOut()
    {
      await HttpContext.Authentication.SignOutAsync(CookieAuthenticationDefaults.AuthenticationScheme);
    }

    Вся остальная логика работы с пользователями и ролями пишется достаточно легко. Вопрос только в том нужно ли городить свой велосипед.
    Ответ написан
    1 комментарий
  • Как правильно передавать объекты в N-layer архитектуре?

    Nipheris
    @Nipheris Куратор тега C#
    GenericRepository и его метод GetAll - это ни о чем. В том смысле, что вам такой репозиторий не нужен - он ничего не делает и ничего не абстрагирует. Вы выставляете IQueryable - и получаете проблемы на свою голову. Да, это очень соблазнительная штука, но таки репозиторий для того, чтобы все возможные запросы оставлять там, иначе они уходят далеко в логику приложения. Вам нужен конкретный репозиторий (интерфейс GenericRepository может и пригодится) с конкретными запросами, возвращающими IEnumerable. В этом и его суть - на уровне репозитория делается ПЕРВИЧНАЯ выборка (с помощью IQueryable), которая по сути есть запрос к БД и материализация всех НУЖНЫХ объектов, а потом уже мелкую фильтрацию можно делать с объектами в IEnumerable коллекции.

    Как организовать передачу сложных объектов (НЕ СУЩНОСТЕЙ) с уровня DAL на уровень BLL?

    Я бы сделал свой репозиторий для каждой такой вещи. Он будет ОТЛИЧАТЬСЯ от репозитория для сущностей, т.к. там не будет, например, Update. Это будет репозиторий ЗАПИСЕЙ, не объектов. В остальном все также - все возможные запросы нужно постараться собрать там. И класс тоже можно и нужно завести вроде BookReport, только он будет immutable, т.е. будет вести себя как запись. А дальше уже делайте с ним что пожелаете.

    Но если такая выборка находится в репозитории, получается метод репозитория должен возвращать List и уровень DAL будет связан с уровнем BLL.

    Вот тут не понял. Ну пусть возвращает List или IEnumerable, в чем тут вы связь видите?

    Вообще, возможно вам нужно поменьше париться о разделении DAL и BLL. Как правило это приводит к anemic data model, и ничего кроме вреда это вам не принисет. Вообще не знаю откуда эта мода пошла, у меня всегда получалось 80% логики оставлять в самих классах сущностей, и все было ок.
    Ответ написан
    1 комментарий