Compare commits

...

18 Commits

Author SHA1 Message Date
Mattermost Build
1c65b2d53c Update fastlane and set SPACESHIP_SKIP_2FA_UPGRADE (#5190) (#5191)
* Update gems

* Set SPACESHIP_SKIP_2FA_UPGRADE

(cherry picked from commit 0f120f8e26)

Co-authored-by: Miguel Alatzar <migbot@users.noreply.github.com>
2021-02-25 12:26:05 -07:00
Weblate (bot)
430d59c247 Translations update from Weblate (#5179)
* Translated using Weblate (German)

Currently translated at 91.9% (605 of 658 strings)

Translation: mattermost-languages-shipped/mattermost-mobile
Translate-URL: https://translate.mattermost.com/projects/mattermost/mattermost-mobile_master/de/

* Translated using Weblate (French)

Currently translated at 91.0% (599 of 658 strings)

Translation: mattermost-languages-shipped/mattermost-mobile
Translate-URL: https://translate.mattermost.com/projects/mattermost/mattermost-mobile_master/fr/

* Translated using Weblate (Dutch)

Currently translated at 100.0% (662 of 662 strings)

Translation: mattermost-languages-shipped/mattermost-mobile
Translate-URL: https://translate.mattermost.com/projects/mattermost/mattermost-mobile_master/nl/

Translated using Weblate (Dutch)

Currently translated at 99.8% (661 of 662 strings)

Translation: mattermost-languages-shipped/mattermost-mobile
Translate-URL: https://translate.mattermost.com/projects/mattermost/mattermost-mobile_master/nl/

* Translated using Weblate (Turkish)

Currently translated at 100.0% (662 of 662 strings)

Translation: mattermost-languages-shipped/mattermost-mobile
Translate-URL: https://translate.mattermost.com/projects/mattermost/mattermost-mobile_master/tr/

* Translated using Weblate (Chinese (Simplified))

Currently translated at 100.0% (662 of 662 strings)

Translation: mattermost-languages-shipped/mattermost-mobile
Translate-URL: https://translate.mattermost.com/projects/mattermost/mattermost-mobile_master/zh_Hans/

* Translated using Weblate (Swedish)

Currently translated at 100.0% (662 of 662 strings)

Translation: mattermost-languages-shipped/mattermost-mobile
Translate-URL: https://translate.mattermost.com/projects/mattermost/mattermost-mobile_master/sv/

* Translated using Weblate (Bulgarian)

Currently translated at 100.0% (662 of 662 strings)

Translation: mattermost-languages-shipped/mattermost-mobile
Translate-URL: https://translate.mattermost.com/projects/mattermost/mattermost-mobile_master/bg/

* Translated using Weblate (Portuguese (Brazil))

Currently translated at 100.0% (662 of 662 strings)

Translation: mattermost-languages-shipped/mattermost-mobile
Translate-URL: https://translate.mattermost.com/projects/mattermost/mattermost-mobile_master/pt_BR/

Co-authored-by: Simon Erni <mattermost@erni.io>
Co-authored-by: William Farelly <wfarelly@orange.fr>
Co-authored-by: Tom De Moor <tom@controlaltdieliet.be>
Co-authored-by: Kaya Zeren <kayazeren@gmail.com>
Co-authored-by: aeomin <lin@aeomin.net>
Co-authored-by: majo <martinjohnson@bahnhof.se>
Co-authored-by: Nikolai Zahariev <nikolaiz@yahoo.com>
Co-authored-by: rodrigocorsi <rodrigocorsi@gmail.com>
2021-02-15 22:09:28 +01:00
Mattermost Build
e782475d1c Bump app build number to 345 (#5173) (#5174)
(cherry picked from commit 43645d781e)

Co-authored-by: Miguel Alatzar <migbot@users.noreply.github.com>
2021-02-10 15:12:00 -07:00
Mattermost Build
8aa6422d63 Add retriable FastImage component (#5167) (#5172)
(cherry picked from commit e33a16d4f1)

Co-authored-by: Miguel Alatzar <migbot@users.noreply.github.com>
2021-02-10 14:54:17 -07:00
Mattermost Build
ae7f06bfd3 [MM-32734] Convert value to string to prevent crash (#5164) (#5171)
* Convert value to string

* Add default value prop

(cherry picked from commit ed4b100962)

Co-authored-by: Miguel Alatzar <migbot@users.noreply.github.com>
2021-02-10 14:48:15 -07:00
Mattermost Build
79ea18e55e Place (you) before username (#5168) (#5170)
(cherry picked from commit 5101927e45)

Co-authored-by: Miguel Alatzar <migbot@users.noreply.github.com>
2021-02-10 14:25:40 -07:00
Weblate (bot)
745b8718f7 Translations update from Weblate (#5161)
* Translated using Weblate (Portuguese (Brazil))

Currently translated at 98.3% (647 of 658 strings)

Translation: mattermost-languages-shipped/mattermost-mobile
Translate-URL: https://translate.mattermost.com/projects/mattermost/mattermost-mobile_master/pt_BR/

* Translated using Weblate (Swedish)

Currently translated at 100.0% (658 of 658 strings)

Translation: mattermost-languages-shipped/mattermost-mobile
Translate-URL: https://translate.mattermost.com/projects/mattermost/mattermost-mobile_master/sv/

Co-authored-by: rodrigocorsi <rodrigocorsi@gmail.com>
Co-authored-by: majo <martinjohnson@bahnhof.se>
2021-02-08 23:44:35 +01:00
Mattermost Build
19563276fa Bump app build number to 344 (#5158) (#5159)
(cherry picked from commit 70a8cf0651)

Co-authored-by: Miguel Alatzar <migbot@users.noreply.github.com>
2021-02-05 11:41:47 -07:00
Mattermost Build
07cbd77af0 [MM-32587] [MM32602] Downgrade react-native-elements (#5156) (#5157)
* Downgrade react-native-elements

* Trigger Build

* Update package-lock.json

(cherry picked from commit e4b2183781)

Co-authored-by: Miguel Alatzar <migbot@users.noreply.github.com>
2021-02-05 11:14:01 -07:00
Mattermost Build
32e1ce0573 Prevent double tap of send button (#5154) (#5155)
(cherry picked from commit a17aff9c95)

Co-authored-by: Miguel Alatzar <migbot@users.noreply.github.com>
2021-02-04 11:59:27 -07:00
Weblate (bot)
43f6c0869a Translated using Weblate (Chinese (Simplified)) (#5152)
Currently translated at 100.0% (658 of 658 strings)

Translation: mattermost-languages-shipped/mattermost-mobile
Translate-URL: https://translate.mattermost.com/projects/mattermost/mattermost-mobile_master/zh_Hans/

Co-authored-by: aeomin <lin@aeomin.net>
2021-02-03 01:08:07 +01:00
Mattermost Build
9244571ca1 Bump app build number to 343 (#5151) (#5153)
(cherry picked from commit 9da0f43417)

Co-authored-by: Miguel Alatzar <migbot@users.noreply.github.com>
2021-02-01 15:10:07 -07:00
Mattermost Build
1cca1b8281 MM-32254 Update CommonMark and fix handling of deeply nested Markdown (#5148) (#5150)
* MM-32254 Update commonmark.js fork from upstream

* MM-32254 Fix handling of partially rendered Markdown tree

(cherry picked from commit 63b0e6043f)

Co-authored-by: Harrison Healey <harrisonmhealey@gmail.com>
2021-02-01 11:39:53 -07:00
Mattermost Build
641ba445f9 Bump app build number to 342 (#5142) (#5143)
(cherry picked from commit a659eb69d9)

Co-authored-by: Miguel Alatzar <migbot@users.noreply.github.com>
2021-01-26 17:56:24 -07:00
Mattermost Build
059f77ad3c Bump app version number to 1.40.0 (#5140) (#5141)
(cherry picked from commit b4a5b54c16)

Co-authored-by: Miguel Alatzar <migbot@users.noreply.github.com>
2021-01-26 17:47:56 -07:00
Mattermost Build
1b6d2038ee [MM-30994] tweak emoji search options for better results (#5120) (#5139)
* [MM-30994] tweak emooji search options for better results

* Apply updated fuse options to emoji picker

Co-authored-by: Miguel Alatzar <this.migbot@gmail.com>
(cherry picked from commit f74e94d6cd)

Co-authored-by: Ashish Bhate <bhate.ashish@gmail.com>
2021-01-26 17:06:05 -07:00
Mattermost Build
48fa3b6331 MM-32183 Fix in-app notification + Android ack (#5132) (#5138)
* MM-32183 Fix in-app notification + Android ack

* comment suggested change

Co-authored-by: Miguel Alatzar <migbot@users.noreply.github.com>

Co-authored-by: Miguel Alatzar <migbot@users.noreply.github.com>
(cherry picked from commit 9568a4592c)

Co-authored-by: Elias Nahum <nahumhbl@gmail.com>
2021-01-26 14:29:59 -07:00
Mattermost Build
b93e66e896 MM-31990 fix limit reacting to a post to 40 different emojis (#5121) (#5129)
* MM-31990 fix limit reacting to a post to 40 different emojis

* Fix selector

(cherry picked from commit 5381062bfa)

Co-authored-by: Elias Nahum <nahumhbl@gmail.com>
2021-01-22 12:55:11 -03:00
35 changed files with 367 additions and 132 deletions

View File

@@ -132,8 +132,8 @@ android {
minSdkVersion rootProject.ext.minSdkVersion
targetSdkVersion rootProject.ext.targetSdkVersion
missingDimensionStrategy "RNNotifications.reactNativeVersion", "reactNative60"
versionCode 341
versionName "1.39.0"
versionCode 345
versionName "1.40.0"
multiDexEnabled = true
testBuildType System.getProperty('testBuildType', 'debug')
testInstrumentationRunner 'androidx.test.runner.AndroidJUnitRunner'

View File

@@ -37,6 +37,11 @@ public class MattermostCredentialsHelper {
HashMap<String, String> asyncStorageResults = asyncStorage.multiGet(asyncStorageKeys);
String serverUrl = asyncStorageResults.get(CURRENT_SERVER_URL);
final WritableMap options = Arguments.createMap();
// KeyChain module fails if `authenticationPrompt` is not set
final WritableMap authPrompt = Arguments.createMap();
authPrompt.putString("title", "Authenticate to retrieve secret");
authPrompt.putString("cancel", "Cancel");
options.putMap("authenticationPrompt", authPrompt);
options.putString("service", serverUrl);
keychainModule.getGenericPasswordForOptions(options, promise);

View File

@@ -137,12 +137,12 @@ const AtMentionItem = (props: AtMentionItemProps) => {
style={style.rowUsername}
numberOfLines={1}
>
{` @${username}`}
{isCurrentUser &&
<FormattedText
id='suggestion.mention.you'
defaultMessage='(you)'
/>}
{` @${username}`}
</Text>
</View>
</TouchableWithFeedback>

View File

@@ -21,9 +21,7 @@ const EMOJI_REGEX = /(^|\s|^\+|^-)(:([^:\s]*))$/i;
const EMOJI_REGEX_WITHOUT_PREFIX = /\B(:([^:\s]*))$/i;
const FUSE_OPTIONS = {
shouldSort: false,
threshold: 0.3,
location: 0,
distance: 10,
ignoreLocation: true,
includeMatches: true,
findAllMatches: true,
};

View File

@@ -46,9 +46,10 @@ describe('components/autocomplete/emoji_suggestion', () => {
});
test('searchEmojis should return the right values on fuse', () => {
const output1 = ['100', '1234', '1st_place_medal', '+1', '-1', 'u7121'];
const output1 = ['100', '1234', '1st_place_medal', '+1', '-1', 'clock1', 'clock10', 'clock1030', 'clock11', 'clock1130', 'clock12', 'clock1230', 'clock130', 'rage1', 'u7121', 'u7981'];
const output2 = ['+1'];
const output3 = ['-1'];
const output3 = ['-1', 'e-mail', 'non-potable_water'];
const output4 = ['checkered_flag', 'ballot_box_with_check', 'heavy_check_mark', 'white_check_mark'];
const wrapper = shallowWithIntl(<EmojiSuggestion {...baseProps}/>);
wrapper.instance().searchEmojis('');
@@ -71,5 +72,11 @@ describe('components/autocomplete/emoji_suggestion', () => {
setTimeout(() => {
expect(wrapper.state('dataSource')).toEqual(output3);
}, 100);
wrapper.instance().searchEmojis('check');
jest.runAllTimers();
setTimeout(() => {
expect(wrapper.state('dataSource')).toEqual(output4);
}, 100);
});
});

View File

@@ -25,9 +25,7 @@ describe('components/emoji_picker/emoji_picker.ios', () => {
const emojisBySection = selectEmojisBySection(state);
const options = {
shouldSort: false,
threshold: 0.3,
location: 0,
distance: 10,
ignoreLocation: true,
includeMatches: true,
findAllMatches: true,
};
@@ -74,7 +72,7 @@ describe('components/emoji_picker/emoji_picker.ios', () => {
test('searchEmojis should return the right values on fuse', async () => {
const input = '1';
const output = ['100', '1234', '1st_place_medal', '+1', '-1', 'u7121'];
const output = ['100', '1234', '1st_place_medal', '+1', '-1', 'clock1', 'clock10', 'clock1030', 'clock11', 'clock1130', 'clock12', 'clock1230', 'clock130', 'rage1', 'u7121', 'u7981'];
const wrapper = shallowWithIntl(<EmojiPicker {...baseProps}/>);
const result = wrapper.instance().searchEmojis(input);

View File

@@ -19,9 +19,7 @@ function mapStateToProps(state) {
const emojis = selectEmojisByName(state);
const options = {
shouldSort: false,
threshold: 0.3,
location: 0,
distance: 10,
ignoreLocation: true,
includeMatches: true,
findAllMatches: true,
};

View File

@@ -73,6 +73,7 @@ export default class Markdown extends PureComponent {
disableChannelLink: false,
disableAtChannelMentionHighlight: false,
disableGallery: false,
value: '',
};
constructor(props) {
@@ -444,7 +445,7 @@ export default class Markdown extends PureComponent {
};
render() {
let ast = this.parser.parse(this.props.value);
let ast = this.parser.parse(this.props.value.toString());
ast = combineTextNodes(ast);
ast = addListItemIndices(ast);

View File

@@ -33,4 +33,26 @@ describe('Markdown', () => {
expect(wrapper.getElement()).toMatchSnapshot();
});
test('MM-32254 should not crash when given string with deeply nested asterisks', () => {
const props = {
...baseProps,
value: '**'.repeat(50) + 'test' + '**'.repeat(50) + 'test',
};
shallow(
<Markdown {...props}/>,
);
});
test('should not crash when given a non-string value', () => {
const props = {
...baseProps,
value: 10,
};
shallow(
<Markdown {...props}/>,
);
});
});

View File

@@ -21,6 +21,7 @@ import EventEmitter from '@mm-redux/utils/event_emitter';
import EphemeralStore from '@store/ephemeral_store';
import * as DraftUtils from '@utils/draft';
import {confirmOutOfOfficeDisabled} from '@utils/status';
import {preventDoubleTap} from '@utils/tap';
import {changeOpacity, makeStyleSheetFromTheme} from '@utils/theme';
const AUTOCOMPLETE_MARGIN = 20;
@@ -228,7 +229,7 @@ export default class DraftInput extends PureComponent {
});
};
handleSendMessage = () => {
handleSendMessage = preventDoubleTap(() => {
if (!this.input.current) {
return;
}
@@ -236,42 +237,44 @@ export default class DraftInput extends PureComponent {
const value = this.input.current.getValue();
this.input.current.resetTextInput();
requestAnimationFrame(() => {
if (!this.isSendButtonEnabled()) {
this.input.current.setValue(value);
return;
}
this.doHandleSendMessage(value);
});
this.setState({sendingMessage: true});
doHandleSendMessage = (value) => requestAnimationFrame(() => {
if (!this.isSendButtonEnabled()) {
this.input.current.setValue(value);
return;
}
const {channelId, files, handleClearFailedFiles, rootId} = this.props;
this.setState({sendingMessage: true});
const isReactionMatch = value.match(IS_REACTION_REGEX);
if (isReactionMatch) {
const emoji = isReactionMatch[2];
this.sendReaction(emoji);
return;
}
const {channelId, files, handleClearFailedFiles, rootId} = this.props;
const hasFailedAttachments = files.some((f) => f.failed);
if (hasFailedAttachments) {
const {formatMessage} = this.context.intl;
const cancel = () => {
this.setInputValue(value);
this.setState({sendingMessage: false});
};
const accept = () => {
// Remove only failed files
handleClearFailedFiles(channelId, rootId);
this.sendMessage(value);
};
const isReactionMatch = value.match(IS_REACTION_REGEX);
if (isReactionMatch) {
const emoji = isReactionMatch[2];
this.sendReaction(emoji);
return;
}
DraftUtils.alertAttachmentFail(formatMessage, accept, cancel);
} else {
const hasFailedAttachments = files.some((f) => f.failed);
if (hasFailedAttachments) {
const {formatMessage} = this.context.intl;
const cancel = () => {
this.setInputValue(value);
this.setState({sendingMessage: false});
};
const accept = () => {
// Remove only failed files
handleClearFailedFiles(channelId, rootId);
this.sendMessage(value);
}
});
}
};
DraftUtils.alertAttachmentFail(formatMessage, accept, cancel);
} else {
this.sendMessage(value);
}
});
isFileLoading = () => {
const {files} = this.props;

View File

@@ -4,14 +4,14 @@
import React, {PureComponent} from 'react';
import PropTypes from 'prop-types';
import {Animated, ImageBackground, Image, Platform, View, StyleSheet} from 'react-native';
import FastImage from 'react-native-fast-image';
import thumb from '@assets/images/thumb.png';
import CustomPropTypes from '@constants/custom_prop_types';
import RetriableFastImage from '@components/retriable_fast_image';
import {changeOpacity, makeStyleSheetFromTheme} from '@utils/theme';
const AnimatedImageBackground = Animated.createAnimatedComponent(ImageBackground);
const AnimatedFastImage = Animated.createAnimatedComponent(FastImage);
const AnimatedFastImage = Animated.createAnimatedComponent(RetriableFastImage);
export default class ProgressiveImage extends PureComponent {
static propTypes = {

View File

@@ -4,6 +4,8 @@
import {connect} from 'react-redux';
import {bindActionCreators} from 'redux';
import {addReaction} from '@actions/views/emoji';
import {MAX_ALLOWED_REACTIONS} from '@constants/emoji';
import {removeReaction} from '@mm-redux/actions/posts';
import {makeGetReactionsForPost, getPost} from '@mm-redux/selectors/entities/posts';
import {haveIChannelPermission} from '@mm-redux/selectors/entities/roles';
@@ -12,9 +14,7 @@ import Permissions from '@mm-redux/constants/permissions';
import {getCurrentUserId} from '@mm-redux/selectors/entities/users';
import {getTheme} from '@mm-redux/selectors/entities/preferences';
import {getChannel, isChannelReadOnlyById} from '@mm-redux/selectors/entities/channels';
import {addReaction} from 'app/actions/views/emoji';
import {MAX_ALLOWED_REACTIONS} from 'app/constants/emoji';
import {selectEmojisCountFromReactions} from '@selectors/emojis';
import Reactions from './reactions';
@@ -46,10 +46,7 @@ function makeMapStateToProps() {
default: true,
});
if (reactions) {
// On servers without metadata reactions at this point can be undefined
canAddMoreReactions = Object.values(reactions).length < MAX_ALLOWED_REACTIONS;
}
canAddMoreReactions = selectEmojisCountFromReactions(reactions) < MAX_ALLOWED_REACTIONS;
canRemoveReaction = haveIChannelPermission(state, {
team: teamId,

View File

@@ -0,0 +1,41 @@
// Copyright (c) 2015-present Mattermost, Inc. All Rights Reserved.
// See LICENSE.txt for license information.
import React, {PureComponent} from 'react';
import FastImage, {FastImageProps} from 'react-native-fast-image';
export const FAST_IMAGE_MAX_RETRIES = 3;
type RetriableFastImageProps = FastImageProps & {
id: string
}
type RetriableFastImageState = {
retry: number
}
export default class RetriableFastImage extends PureComponent<RetriableFastImageProps, RetriableFastImageState> {
state = {
retry: 0,
}
onError = () => {
const retry = this.state.retry + 1;
if (retry > FAST_IMAGE_MAX_RETRIES && this.props.onError) {
this.props.onError();
return;
}
this.setState({retry});
}
render() {
return (
<FastImage
{...this.props}
key={`${this.props.id}-${this.state.retry}`}
onError={this.onError}
/>
);
}
}

View File

@@ -0,0 +1,52 @@
// Copyright (c) 2015-present Mattermost, Inc. All Rights Reserved.
// See LICENSE.txt for license information.
import React from 'react';
import {shallow} from 'enzyme';
import FastImage from 'react-native-fast-image';
import RetriableFastImage, {FAST_IMAGE_MAX_RETRIES} from './index';
describe('RetriableFastImage', () => {
const baseProps = {
id: 'id',
onError: jest.fn(),
};
it('should update the FastImage element key on error until max retries has been reached', () => {
const wrapper = shallow(
<RetriableFastImage {...baseProps}/>,
);
const instance = wrapper.instance();
let retry = 0;
expect(wrapper.containsMatchingElement(<FastImage key={`${baseProps.id}-${retry}`}/>)).toEqual(true);
while (instance.state.retry < FAST_IMAGE_MAX_RETRIES) {
instance.onError();
retry += 1;
expect(wrapper.containsMatchingElement(<FastImage key={`${baseProps.id}-${retry}`}/>)).toEqual(true);
}
instance.onError();
expect(wrapper.containsMatchingElement(<FastImage key={`${baseProps.id}-${retry}`}/>)).toEqual(true);
});
it('should call props.onError only after max retries has been reached', () => {
const wrapper = shallow(
<RetriableFastImage {...baseProps}/>,
);
const instance = wrapper.instance();
let retry = 0;
while (instance.state.retry < FAST_IMAGE_MAX_RETRIES) {
instance.onError();
retry += 1;
expect(instance.state.retry).toEqual(retry);
expect(baseProps.onError).not.toHaveBeenCalled();
}
instance.onError();
expect(instance.state.retry).toEqual(retry);
expect(baseProps.onError).toHaveBeenCalled();
});
});

View File

@@ -7,6 +7,7 @@ import * as Animatable from 'react-native-animatable';
import {Navigation} from 'react-native-navigation';
import {PanGestureHandler} from 'react-native-gesture-handler';
import {useDispatch} from 'react-redux';
import {useSafeAreaInsets} from 'react-native-safe-area-context';
import {popToRoot, dismissAllModals, dismissOverlay} from '@actions/navigation';
import {loadFromPushNotification} from '@actions/views/root';
@@ -44,6 +45,7 @@ const initialAnimation: SlideAnimation = {
const Notification = ({componentId, notification}: NotificationProps) => {
const [animation, setAnimation] = useState<SlideAnimation>(initialAnimation);
const insets = useSafeAreaInsets();
const dispatch = useDispatch();
const dismissTimerRef = useRef<NodeJS.Timeout | null>(null);
const tapped = useRef<boolean>(false);
@@ -121,7 +123,7 @@ const Notification = ({componentId, notification}: NotificationProps) => {
>
<Animatable.View
duration={250}
style={styles.container}
style={[styles.container, {height: styles.container.height + (insets.top / 2), paddingTop: (insets.top / 2)}]}
useNativeDriver={true}
animation={animation}
testID='in_app_notification.screen'
@@ -190,7 +192,7 @@ const styles = StyleSheet.create({
marginLeft: 10,
...Platform.select({
android: {
marginTop: 17,
marginTop: 5,
height: 50,
},
ios: {

View File

@@ -4,6 +4,9 @@
import {bindActionCreators} from 'redux';
import {connect} from 'react-redux';
import {addReaction} from '@actions/views/emoji';
import {MAX_ALLOWED_REACTIONS} from '@constants/emoji';
import {THREAD} from '@constants/screen';
import {
deletePost,
flagPost,
@@ -23,11 +26,8 @@ import {haveIChannelPermission} from '@mm-redux/selectors/entities/roles';
import {getCurrentTeamId, getCurrentTeamUrl} from '@mm-redux/selectors/entities/teams';
import {canEditPost} from '@mm-redux/utils/post_utils';
import {isMinimumServerVersion} from '@mm-redux/utils/helpers';
import {MAX_ALLOWED_REACTIONS} from 'app/constants/emoji';
import {THREAD} from 'app/constants/screen';
import {addReaction} from 'app/actions/views/emoji';
import {getDimensions} from 'app/selectors/device';
import {getDimensions} from '@selectors/device';
import {selectEmojisCountFromReactions} from '@selectors/emojis';
import PostOptions from './post_options';
@@ -121,17 +121,13 @@ export function makeMapStateToProps() {
canCopyText = true;
}
if (reactions && Object.values(reactions).length >= MAX_ALLOWED_REACTIONS) {
canAddReaction = false;
}
if (!isMinimumServerVersion(serverVersion, 5, 18) || channelIsArchived) {
canMarkAsUnread = false;
}
return {
...getDimensions(state),
canAddReaction,
canAddReaction: canAddReaction && selectEmojisCountFromReactions(reactions) < MAX_ALLOWED_REACTIONS,
canReply,
canCopyPermalink,
canCopyText,

View File

@@ -129,3 +129,16 @@ export const selectEmojisBySection = createSelector(
return emoticons;
},
);
export const selectEmojisCountFromReactions = createSelector(
(reactions) => reactions,
(reactions) => {
if (reactions) {
const names = Object.values(reactions).map((r) => r.emoji_name);
const diff = new Set(names);
return diff.size;
}
return 0;
},
);

View File

@@ -557,6 +557,10 @@
"password_send.reset": "Възстановяване на паролата ми",
"permalink.error.access": "Постоянната връзка води към изтрито съобщение или към канал, до който нямате достъп.",
"permalink.error.link_not_found": "Връзката не е намерена",
"permalink.show_dialog_warn.cancel": "Откажи",
"permalink.show_dialog_warn.description": "На път сте да се присъедините към \"{channel}\", без да сте добавен от администратора на канала. Наистина ли желаете да се присъедините към този частен канал?",
"permalink.show_dialog_warn.join": "Присъедини",
"permalink.show_dialog_warn.title": "Присъединяване в частен канал",
"post_body.check_for_out_of_channel_groups_mentions.message": "не получихте уведомление от това споменаване, тъй като не сте в канала. Също не сте член на групите, свързани с този канал.",
"post_body.check_for_out_of_channel_mentions.link.and": " и ",
"post_body.check_for_out_of_channel_mentions.link.private": "добавете ги към този частен канал",

View File

@@ -559,6 +559,7 @@
"sidebar_right_menu.logout": "Abmelden",
"sidebar_right_menu.report": "Fehler melden",
"signup.email": "E-Mail-Adresse und Passwort",
"signup.google": "Google Apps",
"signup.office365": "Office 365",
"status_dropdown.set_away": "Abwesend",
"status_dropdown.set_dnd": "Nicht stören",

View File

@@ -45,6 +45,7 @@
"channel_notifications.preference.all_activity": "Pour toute activité",
"channel_notifications.preference.header": "Envoyer des notifications",
"channel_notifications.preference.never": "Jamais",
"channel_notifications.preference.save_error": "Impossible de sauvegarder vos préférences de notification. Merci de vérifier votre connexion et de réessayer.",
"combined_system_message.added_to_channel.many_expanded": "{users} et {lastUser} ont été **ajoutés au canal** par {actor}.",
"combined_system_message.added_to_channel.one": "{firstUser} **ajouté au canal** par {actor}.",
"combined_system_message.added_to_channel.one_you": "Vous avez été **ajouté au canal** par {actor}.",

View File

@@ -552,6 +552,10 @@
"password_send.reset": "Reset wachtwoord",
"permalink.error.access": "Permalink behoort toe aan een verwijderd bericht of aan een kanaal waar je geen toegang tot hebt.",
"permalink.error.link_not_found": "Link Niet Gevonden",
"permalink.show_dialog_warn.cancel": "Annuleren",
"permalink.show_dialog_warn.description": "Je staat op het punt om deel te nemen aan \"{channel}\" zonder expliciet toegevoegd te zijn door de kanaal admin. Weet je zeker dat je dit privékanaal wilt binnengaan?",
"permalink.show_dialog_warn.join": "Deelnemen",
"permalink.show_dialog_warn.title": "Word lid van het privékanaal",
"post_body.check_for_out_of_channel_groups_mentions.message": "werd niet verwittigd door deze vermelding omdat deze niet in het kanaal zijn. Zij kunnen niet aan het kanaal toegevoegd worden omdat ze geen lid zijn van de gekoppelde groepen. Om hem aan het kanaal toe te voegen, moeten ze toegevoegd worden aan de gelinkte groepen.",
"post_body.check_for_out_of_channel_mentions.link.and": " en ",
"post_body.check_for_out_of_channel_mentions.link.private": "voeg ze toe aan dit privé-kanaal",

View File

@@ -291,6 +291,7 @@
"mobile.ios.photos_permission_denied_description": "Para salvar imagens e videos na sua galeria, por favor altere suas configurações de permissão.",
"mobile.ios.photos_permission_denied_title": "Acesso a galeria de fotos é necessário",
"mobile.join_channel.error": "Não foi possível entrar no canal {displayName}. Por favor verifique a sua conexão e tente novamente.",
"mobile.link.error.text": "Não é possível abrir o link.",
"mobile.link.error.title": "Erro",
"mobile.loading_channels": "Carregando Canais...",
"mobile.loading_members": "Carregando Membros...",
@@ -298,6 +299,7 @@
"mobile.loading_posts": "Carregando Mensagens...",
"mobile.login_options.choose_title": "Escolha seu método de login",
"mobile.long_post_title": "{channelName} - Post",
"mobile.mailTo.error.text": "Não foi possível abrir um cliente de e-mail.",
"mobile.mailTo.error.title": "Erro",
"mobile.managed.blocked_by": "Bloqueado por {vendor}",
"mobile.managed.exit": "Editar",
@@ -344,7 +346,7 @@
"mobile.notification_settings.modal_cancel": "CANCELAR",
"mobile.notification_settings.modal_save": "SALVAR",
"mobile.notification_settings.ooo_auto_responder": "Respostas Automáticas para Mensagens Diretas",
"mobile.notification_settings.save_failed_description": "As configurações de notificação não conseguiram salvar devido a um problema de conexão, tente novamente.",
"mobile.notification_settings.save_failed_description": "As configurações de notificação não conseguiram salvar devido a um problema de conexão. Por favor tente novamente.",
"mobile.notification_settings.save_failed_title": "Problema de conexão",
"mobile.notification_settings_mentions.keywords": "Palavras-chave",
"mobile.notification_settings_mentions.keywordsDescription": "Outras palavras que disparam uma menção",
@@ -362,6 +364,13 @@
"mobile.notification_settings_mobile.test": "Envie-me uma notificação de teste",
"mobile.notification_settings_mobile.test_push": "Este é um teste de notificação push",
"mobile.notification_settings_mobile.vibrate": "Vibrar",
"mobile.oauth.failed_to_login": "Sua tentativa de login falhou. Por favor, tente novamente.",
"mobile.oauth.failed_to_open_link": "O link falhou ao abrir. Por favor, tente novamente.",
"mobile.oauth.restart_login": "Reiniciar o login",
"mobile.oauth.something_wrong": "Algo deu errado",
"mobile.oauth.something_wrong.okButon": "OK",
"mobile.oauth.switch_to_browser": "Por favor use seu navegador para completar o processo de login.",
"mobile.oauth.try_again": "Tentar novamente",
"mobile.offlineIndicator.connected": "Conectado",
"mobile.offlineIndicator.connecting": "Conectando...",
"mobile.offlineIndicator.offline": "Sem conexão com a internet",
@@ -469,6 +478,7 @@
"mobile.server_link.error.title": "Erro Link",
"mobile.server_link.unreachable_channel.error": "Este link pertence a uma mensagem apagada ou a um canal do qual você não tem acesso.",
"mobile.server_link.unreachable_team.error": "Este link pertence a uma mensagem apagada ou a um canal do qual você não tem acesso.",
"mobile.server_link.unreachable_user.error": "Este link pertence a um úsuario excluído.",
"mobile.server_ssl.error.text": "O certificado de {host} não é confiável.\n\nEntre em contato com o Administrador do Sistema para resolver os problemas de certificado e permitir conexões com este servidor.",
"mobile.server_ssl.error.title": "Certificado Não Confiável",
"mobile.server_upgrade.alert_description": "Esta versão do servidor não é suportada e os usuários serão expostos a problemas de compatibilidade que causam falhas ou erros graves que quebram a funcionalidade principal do aplicativo. É necessário atualizar para a versão do servidor {serverVersion} ou posterior.",
@@ -554,6 +564,10 @@
"password_send.reset": "Redefinir minha senha",
"permalink.error.access": "O permalink pertence a uma mensagem deletada ou a um canal o qual você não tem acesso.",
"permalink.error.link_not_found": "Link Não Encontrado",
"permalink.show_dialog_warn.cancel": "Cancelar",
"permalink.show_dialog_warn.description": "Você está prestes a entrar em \"{channel}\" sem ser explicitamente adicionado pelo administrador do canal. Tem certeza de que deseja entrar neste canal privado?",
"permalink.show_dialog_warn.join": "Juntar",
"permalink.show_dialog_warn.title": "Junte-se ao canal privado",
"post_body.check_for_out_of_channel_groups_mentions.message": "não foi notificado por esta menção porque não estão no canal. Eles não podem ser adicionados ao canal porque não são membros dos grupos vinculados. Para adicioná-los a este canal, eles devem ser adicionados aos grupos vinculados.",
"post_body.check_for_out_of_channel_mentions.link.and": " e ",
"post_body.check_for_out_of_channel_mentions.link.private": "adicionar a este canal privado",
@@ -588,6 +602,7 @@
"sidebar_right_menu.logout": "Sair",
"sidebar_right_menu.report": "Relatar um Problema",
"signup.email": "Email e Senha",
"signup.google": "Google Apps",
"signup.office365": "Office 365",
"status_dropdown.set_away": "Ausente",
"status_dropdown.set_dnd": "Não Perturbe",

View File

@@ -87,7 +87,7 @@
"create_post.write": "Skriv till {channelDisplayName}",
"date_separator.today": "Idag",
"date_separator.yesterday": "Igår",
"edit_post.editPost": "Editera meddelandet...",
"edit_post.editPost": "Redigera meddelandet...",
"edit_post.save": "Spara",
"file_upload.fileAbove": "Filer måste vara mindre än {max}MB",
"gallery.download_file": "Ladda ner fil",
@@ -557,6 +557,10 @@
"password_send.reset": "Återställ lösenord",
"permalink.error.access": "Permalänken går till ett borttaget meddelande eller till en kanal du saknar behörighet till.",
"permalink.error.link_not_found": "Länken hittades inte",
"permalink.show_dialog_warn.cancel": "Avbryt",
"permalink.show_dialog_warn.description": "Du är på väg att gå med i \"{channel}\" utan att uttryckligen blivit tillagd av kanalens administratör. Vill du gå med i den här privata kanalen?",
"permalink.show_dialog_warn.join": "Gå med",
"permalink.show_dialog_warn.title": "Gå med i privat kanal",
"post_body.check_for_out_of_channel_groups_mentions.message": "blev inte notifierade av omnämnandet eftersom de inte finns i kanalen. De är inte heller medlemmar i de grupper som länkats till kanalen.",
"post_body.check_for_out_of_channel_mentions.link.and": " och ",
"post_body.check_for_out_of_channel_mentions.link.private": "lägg till dem till denna privata kanal",
@@ -569,12 +573,12 @@
"post_info.auto_responder": "AUTOMATISKT SVAR",
"post_info.bot": "BOT",
"post_info.del": "Ta bort",
"post_info.edit": "Editera",
"post_info.edit": "Redigera",
"post_info.guest": "GÄST",
"post_info.message.show_less": "Visa mindre",
"post_info.message.show_more": "Visa mer",
"post_info.system": "System",
"post_message_view.edited": "(editerad)",
"post_message_view.edited": "(redigerad)",
"posts_view.newMsg": "Nya meddelanden",
"rhs_thread.rootPostDeletedMessage.body": "Delar av denna tråd har raderats utifrån gallringsregler. Det går inte att svara i denna tråd.",
"search_bar.search": "Sök",
@@ -634,12 +638,12 @@
"user.settings.modal.display": "Utseende",
"user.settings.modal.notifications": "Meddelanden",
"user.settings.notifications.allActivity": "För all aktivitet",
"user.settings.notifications.comments": "Mobila notifieringar",
"user.settings.notifications.comments": "Svarsnotifieringar",
"user.settings.notifications.email.disabled": "Notifiering via e-post är inte aktiverat",
"user.settings.notifications.email.everyHour": "Varje timme",
"user.settings.notifications.email.immediately": "Omgående",
"user.settings.notifications.email.never": "Aldrig",
"user.settings.notifications.email.send": "Mobila notifieringar",
"user.settings.notifications.email.send": "Skicka mejlnotifieringar",
"user.settings.notifications.emailInfo": "E-postnotifieringar skickas vid omnämnanden och direktmeddelanden när du är offline eller tillfälligt borta i mer än 5 minuter.",
"user.settings.notifications.never": "Aldrig",
"user.settings.notifications.onlyMentions": "Endast för omnämnanden och direktmeddelanden",

View File

@@ -557,6 +557,10 @@
"password_send.reset": "Parolamı sıfırla",
"permalink.error.access": "Kalıcı bağlantı silinmiş ya da erişiminiz olmayan bir kanaldaki bir iletiye ait.",
"permalink.error.link_not_found": "Bağlantı Bulunamadı",
"permalink.show_dialog_warn.cancel": "İptal",
"permalink.show_dialog_warn.description": "\"{channel}\" kanalına, kanal yöneticisi tarafından açıkça eklenmeden katılmak üzeresiniz. Bu özel kanala katılmak istediğinize emin misiniz?",
"permalink.show_dialog_warn.join": "Katıl",
"permalink.show_dialog_warn.title": "Özel kanala katıl",
"post_body.check_for_out_of_channel_groups_mentions.message": "kanalda bulunmadıkları için bu anma nedeniyle bildirim gönderilmeyecek. İlişkilendirilmiş grupların üyesi olmadıklarından bu kanala eklenemezler. Onları bu kanala eklemek için ilişkilendirilmiş gruplara eklenmeleri gerekir.",
"post_body.check_for_out_of_channel_mentions.link.and": " ve ",
"post_body.check_for_out_of_channel_mentions.link.private": "bu özel kanala eklemek ister misiniz",

View File

@@ -291,12 +291,16 @@
"mobile.ios.photos_permission_denied_description": "上传照片和视频到您的 Mattermost 或保存到您的设备。打开设定并允许 Mattermost 读写到您的相册和视频集。",
"mobile.ios.photos_permission_denied_title": "{applicationName} 想要访问您的照片",
"mobile.join_channel.error": "我们无法加入频道 {displayName}。请检查您的网络连接再尝试。",
"mobile.link.error.text": "无法打开链接。",
"mobile.link.error.title": "错误",
"mobile.loading_channels": "正在加载频道...",
"mobile.loading_members": "正在加载成员...",
"mobile.loading_options": "加载选项中...",
"mobile.loading_posts": "正在加载消息...",
"mobile.login_options.choose_title": "选择您的登入方式",
"mobile.long_post_title": "{channelName} - 消息",
"mobile.mailTo.error.text": "无法打开邮件客户端。",
"mobile.mailTo.error.title": "错误",
"mobile.managed.blocked_by": "被 {vendor} 封锁",
"mobile.managed.exit": "退出",
"mobile.managed.jailbreak": "越狱的设备不被 {vendor} 信任,请退出应用。",
@@ -360,6 +364,13 @@
"mobile.notification_settings_mobile.test": "给我发送个测试通知",
"mobile.notification_settings_mobile.test_push": "这是一个推送通知测试",
"mobile.notification_settings_mobile.vibrate": "震动",
"mobile.oauth.failed_to_login": "登入失败。请重试。",
"mobile.oauth.failed_to_open_link": "打开链接失败。请重试。",
"mobile.oauth.restart_login": "重新登入",
"mobile.oauth.something_wrong": "出现了故障",
"mobile.oauth.something_wrong.okButon": "确定",
"mobile.oauth.switch_to_browser": "请使用您的浏览器以完成登入。",
"mobile.oauth.try_again": "重试",
"mobile.offlineIndicator.connected": "已连接",
"mobile.offlineIndicator.connecting": "正在连接...",
"mobile.offlineIndicator.offline": "无网络连接",
@@ -467,6 +478,7 @@
"mobile.server_link.error.title": "链接错误",
"mobile.server_link.unreachable_channel.error": "此链接属于已删除的频道或者您没有权限访问的频道。",
"mobile.server_link.unreachable_team.error": "此链接属于已删除的团队或者您没有权限访问的团队。",
"mobile.server_link.unreachable_user.error": "该链接属于位已删除的用户。",
"mobile.server_ssl.error.text": "{host} 的证书不可信。\n\n请联系您的系统管理员解决证书问题。",
"mobile.server_ssl.error.title": "不可信任的证书",
"mobile.server_upgrade.alert_description": "此服务器版本不受支持,用户将面临兼容性问题,这些问题会导致崩溃或严重的错误影响应用程序的核心功能。 需要升级到服务器版本 {serverVersion} 或更高。",
@@ -552,6 +564,10 @@
"password_send.reset": "重置我的密码",
"permalink.error.access": "此永久链接指向已删除的消息或者您没有权限访问的频道。",
"permalink.error.link_not_found": "未找到链接",
"permalink.show_dialog_warn.cancel": "取消",
"permalink.show_dialog_warn.description": "您即将加入“ {channel}”,而没有被频道管理员明确添加。您确定要加入此私有频道吗?",
"permalink.show_dialog_warn.join": "加入",
"permalink.show_dialog_warn.title": "加入私有频道",
"post_body.check_for_out_of_channel_groups_mentions.message": "未收到此提及因为他们不在此频道。同时他们也不是此频道关联组的成员。",
"post_body.check_for_out_of_channel_mentions.link.and": " 以及 ",
"post_body.check_for_out_of_channel_mentions.link.private": "添加他们到此私有频道",
@@ -586,6 +602,7 @@
"sidebar_right_menu.logout": "注销",
"sidebar_right_menu.report": "报告问题",
"signup.email": "电子邮箱和密码",
"signup.google": "Google Apps",
"signup.office365": "Office 365",
"status_dropdown.set_away": "离开",
"status_dropdown.set_dnd": "请勿打扰",

View File

@@ -11,6 +11,8 @@ is_build_pr = false
# Executes before anything else use to setup the script
before_all do
ENV['SPACESHIP_SKIP_2FA_UPGRADE'] = '1'
is_build_pr = ENV['BUILD_PR'] == 'true'
if is_build_pr && ENV['CIRCLECI'] == 'true'
ENV['BRANCH_TO_BUILD'] = ENV['CIRCLE_BRANCH']

View File

@@ -4,19 +4,20 @@ GEM
CFPropertyList (3.0.3)
addressable (2.7.0)
public_suffix (>= 2.0.2, < 5.0)
artifactory (3.0.15)
atomos (0.1.3)
aws-eventstream (1.1.0)
aws-partitions (1.414.0)
aws-sdk-core (3.110.0)
aws-partitions (1.429.0)
aws-sdk-core (3.112.0)
aws-eventstream (~> 1, >= 1.0.2)
aws-partitions (~> 1, >= 1.239.0)
aws-sigv4 (~> 1.1)
jmespath (~> 1.0)
aws-sdk-kms (1.40.0)
aws-sdk-core (~> 3, >= 3.109.0)
aws-sdk-kms (1.42.0)
aws-sdk-core (~> 3, >= 3.112.0)
aws-sigv4 (~> 1.1)
aws-sdk-s3 (1.87.0)
aws-sdk-core (~> 3, >= 3.109.0)
aws-sdk-s3 (1.88.1)
aws-sdk-core (~> 3, >= 3.112.0)
aws-sdk-kms (~> 1)
aws-sigv4 (~> 1.1)
aws-sigv4 (1.2.2)
@@ -34,8 +35,8 @@ GEM
domain_name (0.5.20190701)
unf (>= 0.0.5, < 1.0.0)
dotenv (2.7.6)
emoji_regex (3.2.1)
excon (0.78.1)
emoji_regex (3.2.2)
excon (0.79.0)
faraday (1.3.0)
faraday-net_http (~> 1.0)
multipart-post (>= 1.2, < 3)
@@ -43,13 +44,14 @@ GEM
faraday-cookie_jar (0.0.7)
faraday (>= 0.8.0)
http-cookie (~> 1.0.0)
faraday-net_http (1.0.0)
faraday-net_http (1.0.1)
faraday_middleware (1.0.0)
faraday (~> 1.0)
fastimage (2.2.1)
fastlane (2.171.0)
fastimage (2.2.2)
fastlane (2.176.0)
CFPropertyList (>= 2.3, < 4.0.0)
addressable (>= 2.3, < 3.0.0)
artifactory (~> 3.0)
aws-sdk-s3 (~> 1.0)
babosa (>= 1.0.3, < 2.0.0)
bundler (>= 1.12.0, < 3.0.0)
@@ -70,6 +72,7 @@ GEM
jwt (>= 2.1.0, < 3)
mini_magick (>= 4.9.4, < 5.0.0)
multipart-post (~> 2.0.0)
naturally (~> 2.2)
plist (>= 3.1.0, < 4.0.0)
rubyzip (>= 2.0.0, < 3.0.0)
security (= 0.1.3)
@@ -97,20 +100,35 @@ GEM
representable (~> 3.0)
retriable (>= 2.0, < 4.0)
signet (~> 0.12)
google-apis-core (0.2.1)
addressable (~> 2.5, >= 2.5.1)
googleauth (~> 0.14)
httpclient (>= 2.8.1, < 3.0)
mini_mime (~> 1.0)
representable (~> 3.0)
retriable (>= 2.0, < 4.0)
rexml
signet (~> 0.14)
webrick
google-apis-iamcredentials_v1 (0.1.0)
google-apis-core (~> 0.1)
google-apis-storage_v1 (0.2.0)
google-apis-core (~> 0.1)
google-cloud-core (1.5.0)
google-cloud-env (~> 1.0)
google-cloud-errors (~> 1.0)
google-cloud-env (1.4.0)
faraday (>= 0.17.3, < 2.0)
google-cloud-errors (1.0.1)
google-cloud-storage (1.29.2)
google-cloud-storage (1.30.0)
addressable (~> 2.5)
digest-crc (~> 0.4)
google-api-client (~> 0.33)
google-apis-iamcredentials_v1 (~> 0.1)
google-apis-storage_v1 (~> 0.1)
google-cloud-core (~> 1.2)
googleauth (~> 0.9)
mini_mime (~> 1.0)
googleauth (0.14.0)
googleauth (0.15.1)
faraday (>= 0.17.3, < 2.0)
jwt (>= 1.4, < 3.0)
memoist (~> 0.16)
@@ -131,8 +149,8 @@ GEM
multi_json (1.15.0)
multipart-post (2.0.0)
nanaimo (0.3.0)
naturally (2.2.0)
nokogiri (1.11.0)
naturally (2.2.1)
nokogiri (1.11.1)
mini_portile2 (~> 2.5.0)
racc (~> 1.4)
os (1.1.1)
@@ -145,11 +163,12 @@ GEM
declarative-option (< 0.2.0)
uber (< 0.2.0)
retriable (3.1.2)
rexml (3.2.4)
rouge (2.0.7)
ruby2_keywords (0.0.2)
ruby2_keywords (0.0.4)
rubyzip (2.3.0)
security (0.1.3)
signet (0.14.0)
signet (0.14.1)
addressable (~> 2.3)
faraday (>= 0.17.3, < 2.0)
jwt (>= 1.5, < 3.0)
@@ -170,6 +189,7 @@ GEM
unf_ext
unf_ext (0.0.7.7)
unicode-display_width (1.7.0)
webrick (1.7.0)
word_wrap (1.0.0)
xcodeproj (1.19.0)
CFPropertyList (>= 2.3.3, < 4.0)

View File

@@ -911,7 +911,7 @@
CODE_SIGN_ENTITLEMENTS = Mattermost/Mattermost.entitlements;
CODE_SIGN_IDENTITY = "iPhone Developer";
"CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer";
CURRENT_PROJECT_VERSION = 341;
CURRENT_PROJECT_VERSION = 345;
DEAD_CODE_STRIPPING = NO;
DEVELOPMENT_TEAM = UQ8HT4Q2XM;
ENABLE_BITCODE = NO;
@@ -953,7 +953,7 @@
CODE_SIGN_ENTITLEMENTS = Mattermost/Mattermost.entitlements;
CODE_SIGN_IDENTITY = "iPhone Developer";
"CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer";
CURRENT_PROJECT_VERSION = 341;
CURRENT_PROJECT_VERSION = 345;
DEAD_CODE_STRIPPING = NO;
DEVELOPMENT_TEAM = UQ8HT4Q2XM;
ENABLE_BITCODE = NO;

View File

@@ -21,7 +21,7 @@
<key>CFBundlePackageType</key>
<string>APPL</string>
<key>CFBundleShortVersionString</key>
<string>1.39.0</string>
<string>1.40.0</string>
<key>CFBundleSignature</key>
<string>????</string>
<key>CFBundleURLTypes</key>
@@ -37,7 +37,7 @@
</dict>
</array>
<key>CFBundleVersion</key>
<string>341</string>
<string>345</string>
<key>ITSAppUsesNonExemptEncryption</key>
<false/>
<key>LSRequiresIPhoneOS</key>

View File

@@ -19,9 +19,9 @@
<key>CFBundlePackageType</key>
<string>XPC!</string>
<key>CFBundleShortVersionString</key>
<string>1.39.0</string>
<string>1.40.0</string>
<key>CFBundleVersion</key>
<string>341</string>
<string>345</string>
<key>NSAppTransportSecurity</key>
<dict>
<key>NSAllowsArbitraryLoads</key>

View File

@@ -19,9 +19,9 @@
<key>CFBundlePackageType</key>
<string>XPC!</string>
<key>CFBundleShortVersionString</key>
<string>1.39.0</string>
<string>1.40.0</string>
<key>CFBundleVersion</key>
<string>341</string>
<string>345</string>
<key>NSExtension</key>
<dict>
<key>NSExtensionPointIdentifier</key>

55
package-lock.json generated
View File

@@ -1,6 +1,6 @@
{
"name": "mattermost-mobile",
"version": "1.39.0",
"version": "1.40.0",
"lockfileVersion": 1,
"requires": true,
"dependencies": {
@@ -12431,19 +12431,26 @@
"integrity": "sha1-3dgA2gxmEnOTzKWVDqloo6rxJTs="
},
"commonmark": {
"version": "github:mattermost/commonmark.js#f6ab98dede6ce4b4e7adea140ac77249bfb2d6ce",
"from": "github:mattermost/commonmark.js#f6ab98dede6ce4b4e7adea140ac77249bfb2d6ce",
"version": "github:mattermost/commonmark.js#d716e1c89e0a6721051df7bc74ad7683e1ae438f",
"from": "github:mattermost/commonmark.js#d716e1c89e0a6721051df7bc74ad7683e1ae438f",
"requires": {
"entities": "~ 1.1.1",
"mdurl": "~ 1.0.1",
"minimist": "~ 1.2.0",
"entities": "~2.0",
"mdurl": "~1.0.1",
"minimist": ">=1.2.2",
"string.prototype.repeat": "^0.2.0",
"xregexp": "4.1.1"
},
"dependencies": {
"entities": {
"version": "2.0.3",
"resolved": "https://registry.npmjs.org/entities/-/entities-2.0.3.tgz",
"integrity": "sha512-MyoZ0jgnLvB2X3Lg5HqpFmn1kybDiIfEQmKzTb5apr51Rb+T3KdmMiqa70T+bhGnyv7bQ6WMj2QMHpGMmlrUYQ=="
}
}
},
"commonmark-react-renderer": {
"version": "github:mattermost/commonmark-react-renderer#3a2ac19cab725ad28b170fdc1d397dddedcf87eb",
"from": "github:mattermost/commonmark-react-renderer#3a2ac19cab725ad28b170fdc1d397dddedcf87eb",
"version": "github:mattermost/commonmark-react-renderer#81af294317ebe19b5cc195d7fbc4f4a58177854c",
"from": "github:mattermost/commonmark-react-renderer#81af294317ebe19b5cc195d7fbc4f4a58177854c",
"requires": {
"in-publish": "^2.0.0",
"lodash.assign": "^4.2.0",
@@ -13920,7 +13927,8 @@
"entities": {
"version": "1.1.2",
"resolved": "https://registry.npmjs.org/entities/-/entities-1.1.2.tgz",
"integrity": "sha512-f2LZMYl1Fzu7YSBKg+RoROelpOaNrcGmE9AZubeDfrCEia483oW4MI4VyFd5VNHIgQ/7qm1I0wUHK1eJnn2y2w=="
"integrity": "sha512-f2LZMYl1Fzu7YSBKg+RoROelpOaNrcGmE9AZubeDfrCEia483oW4MI4VyFd5VNHIgQ/7qm1I0wUHK1eJnn2y2w==",
"dev": true
},
"envinfo": {
"version": "7.7.3",
@@ -26533,20 +26541,19 @@
}
},
"react-native-elements": {
"version": "3.1.0",
"resolved": "https://registry.npmjs.org/react-native-elements/-/react-native-elements-3.1.0.tgz",
"integrity": "sha512-U4CuyO+q2JlduPht4P0xz+oIbw3W53uYPpkMqvlwjJiVoFfwnpbAu+JZL01/7VMe98G4Y8nJImcBh7zK9cb3Uw==",
"version": "2.3.2",
"resolved": "https://registry.npmjs.org/react-native-elements/-/react-native-elements-2.3.2.tgz",
"integrity": "sha512-HygYYmq8JYjk/YYiUwr/64qT64H2xlPBz0JnkGTQwvnnyXZrfkHFopw8rLWCupv3iLLPDzVohvPs0Z5HLdonSQ==",
"requires": {
"@types/react-native-vector-icons": "^6.4.6",
"color": "^3.1.2",
"@types/react-native-vector-icons": "^6.4.5",
"color": "^3.1.0",
"deepmerge": "^4.2.2",
"hoist-non-react-statics": "^3.3.2",
"hoist-non-react-statics": "^3.1.0",
"lodash.isequal": "^4.5.0",
"opencollective-postinstall": "^2.0.3",
"opencollective-postinstall": "^2.0.0",
"prop-types": "^15.7.2",
"react-native-ratings": "^7.3.0",
"react-native-safe-area-context": "^3.1.9",
"react-native-size-matters": "^0.3.1"
"react-native-ratings": "^7.2.0",
"react-native-status-bar-height": "^2.5.0"
},
"dependencies": {
"hoist-non-react-statics": {
@@ -26791,11 +26798,6 @@
"resolved": "https://registry.npmjs.org/react-native-share/-/react-native-share-5.1.0.tgz",
"integrity": "sha512-QGMWOPlwboAGd/5uUh2l0jXIDhZ2q8J4CIa063NDE7ihsZRQlF/w6kd90i3bi6GF6aedvhynqZPmezwqjiyU7g=="
},
"react-native-size-matters": {
"version": "0.3.1",
"resolved": "https://registry.npmjs.org/react-native-size-matters/-/react-native-size-matters-0.3.1.tgz",
"integrity": "sha512-mKOfBLIBFBcs9br1rlZDvxD5+mAl8Gfr5CounwJtxI6Z82rGrMO+Kgl9EIg3RMVf3G855a85YVqHJL2f5EDRlw=="
},
"react-native-slider": {
"version": "0.11.0",
"resolved": "https://registry.npmjs.org/react-native-slider/-/react-native-slider-0.11.0.tgz",
@@ -26804,6 +26806,11 @@
"prop-types": "^15.5.6"
}
},
"react-native-status-bar-height": {
"version": "2.6.0",
"resolved": "https://registry.npmjs.org/react-native-status-bar-height/-/react-native-status-bar-height-2.6.0.tgz",
"integrity": "sha512-z3SGLF0mHT+OlJDq7B7h/jXPjWcdBT3V14Le5L2PjntjjWM3+EJzq2BcXDwV+v67KFNJic5pgA26cCmseYek6w=="
},
"react-native-status-bar-size": {
"version": "0.3.3",
"resolved": "https://registry.npmjs.org/react-native-status-bar-size/-/react-native-status-bar-size-0.3.3.tgz",

View File

@@ -1,6 +1,6 @@
{
"name": "mattermost-mobile",
"version": "1.39.0",
"version": "1.40.0",
"description": "Mattermost Mobile with React Native",
"repository": "git@github.com:mattermost/mattermost-mobile.git",
"author": "Mattermost, Inc.",
@@ -18,8 +18,8 @@
"@rudderstack/rudder-sdk-react-native": "1.0.4",
"@sentry/react-native": "2.1.0",
"analytics-react-native": "1.2.0",
"commonmark": "github:mattermost/commonmark.js#f6ab98dede6ce4b4e7adea140ac77249bfb2d6ce",
"commonmark-react-renderer": "github:mattermost/commonmark-react-renderer#3a2ac19cab725ad28b170fdc1d397dddedcf87eb",
"commonmark": "github:mattermost/commonmark.js#d716e1c89e0a6721051df7bc74ad7683e1ae438f",
"commonmark-react-renderer": "github:mattermost/commonmark-react-renderer#81af294317ebe19b5cc195d7fbc4f4a58177854c",
"core-js": "3.8.2",
"deep-equal": "2.0.5",
"deepmerge": "4.2.2",
@@ -41,7 +41,7 @@
"react-native-cookies": "github:mattermost/react-native-cookies#b35bafc388ae09c83bd875e887daf6a0755e0b40",
"react-native-device-info": "8.0.0",
"react-native-document-picker": "4.2.0",
"react-native-elements": "3.1.0",
"react-native-elements": "2.3.2",
"react-native-exception-handler": "2.10.9",
"react-native-fast-image": "8.3.4",
"react-native-file-viewer": "2.1.4",

View File

@@ -1,5 +1,5 @@
diff --git a/node_modules/react-native-navigation/lib/android/app/src/main/java/com/reactnativenavigation/react/NavigationModule.java b/node_modules/react-native-navigation/lib/android/app/src/main/java/com/reactnativenavigation/react/NavigationModule.java
index 3bfbc0b..cdb0d05 100644
index 2d8f1ba..708f130 100644
--- a/node_modules/react-native-navigation/lib/android/app/src/main/java/com/reactnativenavigation/react/NavigationModule.java
+++ b/node_modules/react-native-navigation/lib/android/app/src/main/java/com/reactnativenavigation/react/NavigationModule.java
@@ -55,14 +55,18 @@ public class NavigationModule extends ReactContextBaseJavaModule {
@@ -29,7 +29,7 @@ index 3bfbc0b..cdb0d05 100644
}
});
}
@@ -196,8 +200,12 @@ public class NavigationModule extends ReactContextBaseJavaModule {
@@ -201,8 +205,12 @@ public class NavigationModule extends ReactContextBaseJavaModule {
protected void handle(Runnable task) {
UiThread.post(() -> {
@@ -44,11 +44,34 @@ index 3bfbc0b..cdb0d05 100644
}
});
}
diff --git a/node_modules/react-native-navigation/lib/ios/RNNOverlayWindow.m b/node_modules/react-native-navigation/lib/ios/RNNOverlayWindow.m
index 815e1c6..a35a087 100644
--- a/node_modules/react-native-navigation/lib/ios/RNNOverlayWindow.m
+++ b/node_modules/react-native-navigation/lib/ios/RNNOverlayWindow.m
@@ -1,5 +1,7 @@
#import "RNNOverlayWindow.h"
#import "RNNReactView.h"
+#import <react-native-safe-area-context/RNCSafeAreaView.h>
+#import <react-native-safe-area-context/RNCSafeAreaProvider.h>
@implementation RNNOverlayWindow
@@ -7,7 +9,9 @@ - (UIView *)hitTest:(CGPoint)point withEvent:(UIEvent *)event {
UIView *hitTestResult = [super hitTest:point withEvent:event];
if ([hitTestResult isKindOfClass:[UIWindow class]] ||
- [hitTestResult.subviews.firstObject isKindOfClass:RNNReactView.class]) {
+ [hitTestResult.subviews.firstObject isKindOfClass:RNNReactView.class] ||
+ [hitTestResult isKindOfClass:[RNCSafeAreaView class]] ||
+ [hitTestResult isKindOfClass:[RNCSafeAreaProvider class]]) {
return nil;
}
diff --git a/node_modules/react-native-navigation/lib/ios/RNNViewLocation.m b/node_modules/react-native-navigation/lib/ios/RNNViewLocation.m
index f5187d9..d97e766 100644
index 6b9981d..f725701 100644
--- a/node_modules/react-native-navigation/lib/ios/RNNViewLocation.m
+++ b/node_modules/react-native-navigation/lib/ios/RNNViewLocation.m
@@ -32,11 +32,7 @@ - (CGFloat)getClippedCornerRadius:(UIView *)view {
@@ -31,11 +31,7 @@ - (CGFloat)getClippedCornerRadius:(UIView *)view {
- (CATransform3D)getTransform:(UIView *)view {
if (view) {