When you update your app to v5.0, you cannot use setState
method of the ConfigState
. See that code to learn how it can be done in v5.0.
Hi,
You can use a method like below:
login(params: LoginParams): Observable<any> {
const router = this.injector.get(Router);
const tenant = this.sessionState.getTenant();
return from(
this.oAuthService.fetchTokenUsingPasswordFlow(
params.username,
params.password,
new HttpHeaders({ ...(tenant && tenant.id && { __tenant: tenant.id }) }), // add headers here
),
).pipe(
switchMap(() => this.appConfigService.get()),
tap(res => {
this.configState.setState(res);
this.setRememberMe(params.rememberMe);
if (params.redirectUrl) router.navigate([params.redirectUrl]);
}),
);
}
Resource: https://github.com/abpframework/abp/blob/73723bfa26b6709fbf908145df8aece8d25fe5bf/npm/ng-packs/packages/core/src/lib/strategies/auth-flow.strategy.ts#L190-L208
Hi @Jeroenmin
Can you share EntityPropContributors
and FormPropContributors
code so that I can find a solution?
You can check the documents below: Data Table Column (or Entity Prop) Extensions for Angular UI Dynamic Form (or Form Prop) Extensions for Angular UI
Hi,
It will probably be resolved in v5.0. Thanks for your understanding.
Hi,
You need to replace the current user component to achieve this Follow the steps below to replace:
yarn ng generate module current-user --module app
yarn ng generate component current-user --export
import { CoreModule } from '@abp/ng.core';
import { CommonModule } from '@angular/common';
import { NgModule } from '@angular/core';
import { NgbDropdownModule } from '@ng-bootstrap/ng-bootstrap';
import { ThemeLeptonModule } from '@volo/abp.ng.theme.lepton';
import { CurrentUserComponent } from './current-user.component';
@NgModule({
declarations: [CurrentUserComponent],
imports: [CommonModule, ThemeLeptonModule, CoreModule, NgbDropdownModule],
exports: [CurrentUserComponent],
})
export class CurrentUserModule {}
current-user.component.ts
with the following:import {
AuthService,
ConfigStateService,
EnvironmentService,
NAVIGATE_TO_MANAGE_PROFILE,
SessionStateService,
} from '@abp/ng.core';
import { Component, Inject, Optional } from '@angular/core';
import {
NAVIGATE_TO_MY_SECURITY_LOGS,
OPEN_MY_LINK_USERS_MODAL,
} from '@volo/abp.commercial.ng.ui/config';
import { eThemeLeptonComponents } from '@volo/abp.ng.theme.lepton';
@Component({
selector: 'app-current-user',
templateUrl: 'current-user.component.html',
})
export class CurrentUserComponent {
currentUser$ = this.configState.getOne$('currentUser');
selectedTenant$ = this.sessionState.getTenant$();
currentUserImageComponentKey = eThemeLeptonComponents.CurrentUserImage;
get smallScreen(): boolean {
return window.innerWidth < 992;
}
get issuer() {
return this.environment.getEnvironment().oAuthConfig.issuer;
}
constructor(
@Inject(NAVIGATE_TO_MANAGE_PROFILE) public navigateToManageProfile,
@Inject(NAVIGATE_TO_MY_SECURITY_LOGS) public navigateToMySecurityLogs,
@Optional() @Inject(OPEN_MY_LINK_USERS_MODAL) public openMyLinkUsersModal,
private authService: AuthService,
private sessionState: SessionStateService,
private configState: ConfigStateService,
private environment: EnvironmentService,
) {}
navigateToLogin() {
this.authService.navigateToLogin();
}
logout() {
this.authService.logout().subscribe();
}
}
current-user.component.html
with the following:<ng-container *ngIf="currentUser$ | async as user">
<ng-template #loginBtn>
<a role="button" class="btn" (click)="navigateToLogin()">
<i class="fas fa-sign-in-alt mr-1"></i>
{{ 'AbpAccount::Login' | abpLocalization }}</a
>
</ng-template>
<div *ngIf="user.isAuthenticated; else loginBtn" class="dropdown btn-group" ngbDropdown>
<a ngbDropdownToggle class="btn pointer d-flex">
<abp-current-user-image
*abpReplaceableTemplate="{
componentKey: currentUserImageComponentKey,
inputs: { currentUser: { value: user }, classes: { value: 'user-avatar' } }
}"
classes="user-avatar"
></abp-current-user-image>
<span class="ml-1">
<small *ngIf="(selectedTenant$ | async)?.name as tenantName"
><i>{{ tenantName }}</i
>\</small
>
<span>{{ user.userName }}</span>
</span>
</a>
<div ngbDropdownMenu class="dropdown-menu dropdown-menu-right">
<div class="p-2 row">
<div class="pr-0 col col-auto">
<abp-current-user-image
*abpReplaceableTemplate="{
componentKey: currentUserImageComponentKey,
inputs: { currentUser: { value: user }, classes: { value: 'user-avatar-big' } }
}"
classes="user-avatar-big"
></abp-current-user-image>
</div>
<div class="pl-2 col">
<span>{{ 'AbpAccount::Welcome' | abpLocalization }}</span
><br />
<small *ngIf="(selectedTenant$ | async)?.name as tenantName"
><i>{{ tenantName }}</i
>\</small
>
<strong>{{
((user.name || '') + ' ' + (user.surName || '')).trim() || user.userName
}}</strong>
</div>
</div>
<div class="dropdown-divider"></div>
<a
*ngIf="openMyLinkUsersModal"
class="dropdown-item pointer"
(click)="openMyLinkUsersModal()"
>{{ 'AbpAccount::LinkedAccounts' | abpLocalization }}</a
>
<a class="dropdown-item pointer" (click)="navigateToManageProfile()">{{
'AbpAccount::MyAccount' | abpLocalization
}}</a>
<a class="dropdown-item pointer" (click)="navigateToMySecurityLogs()">{{
'AbpAccount::MySecurityLogs' | abpLocalization
}}</a>
<a class="dropdown-item pointer" id="logout" (click)="logout()">{{
'AbpUi::Logout' | abpLocalization
}}</a>
</div>
</div>
</ng-container>
import { NavItemsService } from '@abp/ng.theme.shared';
import { Component } from '@angular/core';
import { eThemeLeptonComponents } from '@volo/abp.ng.theme.lepton';
import { CurrentUserComponent } from './current-user/current-user.component';
@Component({
selector: 'app-root',
template: `
<abp-loader-bar></abp-loader-bar>
<abp-dynamic-layout></abp-dynamic-layout>
`,
})
export class AppComponent {
constructor(private navItems: NavItemsService) {
this.navItems.patchItem(eThemeLeptonComponents.CurrentUser, {
component: CurrentUserComponent,
});
}
}
After the replacement, you can modify the current user component as you wish. Sorry for the late response. Regards.
Hi,
Can you try adding requireHttps: false
to oAuthConfig
property of the environment?
Hi @can.ercan
Please see the environment document.
Hello @GregB
There are two ways to achieve this:
if(!this.form.valid)
{
Object.values(this.form.controls).forEach((control) => {
control.markAsDirty();
control.updateValueAndValidity();
});
return;
}
ngx-validate
's valiteOnSubmit
directive. See the working example:
https://stackblitz.com/edit/ngx-validate?file=src/app/components/app.component.htmlHi @paul.harriman,
DateTimePickerComponent
uses with dynamic form extensions. I don't suggest you to use it. You can combine ng-bootstrap's date picker and time picker components to create your own date time picker component.
DateTimePickerComponent
looks like this:
Hi,
We are working to redirect the user to the login page when the token expires. We are having some issues with the authorization code flow. We'll let you know when the issue is resolved.
Thanks!